mirror of
				https://github.com/cmderdev/cmder.git
				synced 2025-11-04 11:22:13 +08:00 
			
		
		
		
	Merge pull request #2556 from chrisant996/clink-async-prompt
This commit is contained in:
		
							
								
								
									
										101
									
								
								vendor/clink.lua
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										101
									
								
								vendor/clink.lua
									
									
									
									
										vendored
									
									
								
							@@ -63,6 +63,32 @@ local function get_folder_name(path)
 | 
				
			|||||||
end
 | 
					end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					-- Forward/backward compatibility for Clink asynchronous prompt filtering.
 | 
				
			||||||
 | 
					-- With Clink v1.2.10 and higher this lets git status run in the background and
 | 
				
			||||||
 | 
					-- refresh the prompt when it finishes, to eliminate waits in large git repos.
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					local io_popenyield
 | 
				
			||||||
 | 
					local clink_promptcoroutine
 | 
				
			||||||
 | 
					local cached_info = {}
 | 
				
			||||||
 | 
					if clink.promptcoroutine and io.popenyield then
 | 
				
			||||||
 | 
					    io_popenyield = io.popenyield
 | 
				
			||||||
 | 
					    clink_promptcoroutine = clink.promptcoroutine
 | 
				
			||||||
 | 
					else
 | 
				
			||||||
 | 
					    io_popenyield = io.popen
 | 
				
			||||||
 | 
					    clink_promptcoroutine = function (func)
 | 
				
			||||||
 | 
					        return func(false)
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					-- Global variable so other Lua scripts can detect whether they're in a Cmder
 | 
				
			||||||
 | 
					-- shell session.
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					CMDER_SESSION = true
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
---
 | 
					---
 | 
				
			||||||
-- Setting the prompt in clink means that commands which rewrite the prompt do
 | 
					-- Setting the prompt in clink means that commands which rewrite the prompt do
 | 
				
			||||||
-- not destroy our own prompt. It also means that started cmds (or batch files
 | 
					-- not destroy our own prompt. It also means that started cmds (or batch files
 | 
				
			||||||
@@ -113,6 +139,10 @@ local function set_prompt_filter()
 | 
				
			|||||||
      prompt_singleLine = false
 | 
					      prompt_singleLine = false
 | 
				
			||||||
    end
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if prompt_includeVersionControl == nil then
 | 
				
			||||||
 | 
					      prompt_includeVersionControl = true
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    if prompt_type == 'folder' then
 | 
					    if prompt_type == 'folder' then
 | 
				
			||||||
        cwd = get_folder_name(cwd)
 | 
					        cwd = get_folder_name(cwd)
 | 
				
			||||||
    end
 | 
					    end
 | 
				
			||||||
@@ -133,7 +163,12 @@ local function set_prompt_filter()
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
    if env ~= nil then env = "("..env..") " else env = "" end
 | 
					    if env ~= nil then env = "("..env..") " else env = "" end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    prompt = get_uah_color() .. "{uah}" .. get_cwd_color() .. "{cwd}{git}{hg}{svn}" .. get_lamb_color() .. cr .. "{lamb} \x1b[0m"
 | 
					    if uah ~= '' then uah = get_uah_color() .. uah end
 | 
				
			||||||
 | 
					    if cwd ~= '' then cwd = get_cwd_color() .. cwd end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    local version_control = prompt_includeVersionControl and "{git}{hg}{svn}" or ""
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    prompt = "{uah}{cwd}" .. version_control .. get_lamb_color() .. cr .. "{lamb} \x1b[0m"
 | 
				
			||||||
    prompt = string.gsub(prompt, "{uah}", uah)
 | 
					    prompt = string.gsub(prompt, "{uah}", uah)
 | 
				
			||||||
    prompt = string.gsub(prompt, "{cwd}", cwd)
 | 
					    prompt = string.gsub(prompt, "{cwd}", cwd)
 | 
				
			||||||
    prompt = string.gsub(prompt, "{env}", env)
 | 
					    prompt = string.gsub(prompt, "{env}", env)
 | 
				
			||||||
@@ -308,7 +343,7 @@ end
 | 
				
			|||||||
-- @return {bool}
 | 
					-- @return {bool}
 | 
				
			||||||
---
 | 
					---
 | 
				
			||||||
local function get_git_status()
 | 
					local function get_git_status()
 | 
				
			||||||
    local file = io.popen("git --no-optional-locks status --porcelain 2>nul")
 | 
					    local file = io_popenyield("git --no-optional-locks status --porcelain 2>nul")
 | 
				
			||||||
    for line in file:lines() do
 | 
					    for line in file:lines() do
 | 
				
			||||||
        file:close()
 | 
					        file:close()
 | 
				
			||||||
        return false
 | 
					        return false
 | 
				
			||||||
@@ -323,7 +358,7 @@ end
 | 
				
			|||||||
-- @return {bool} indicating true for conflict, false for no conflicts
 | 
					-- @return {bool} indicating true for conflict, false for no conflicts
 | 
				
			||||||
---
 | 
					---
 | 
				
			||||||
function get_git_conflict()
 | 
					function get_git_conflict()
 | 
				
			||||||
    local file = io.popen("git diff --name-only --diff-filter=U 2>nul")
 | 
					    local file = io_popenyield("git diff --name-only --diff-filter=U 2>nul")
 | 
				
			||||||
    for line in file:lines() do
 | 
					    for line in file:lines() do
 | 
				
			||||||
        file:close()
 | 
					        file:close()
 | 
				
			||||||
        return true;
 | 
					        return true;
 | 
				
			||||||
@@ -363,11 +398,36 @@ local function get_svn_status()
 | 
				
			|||||||
    return true
 | 
					    return true
 | 
				
			||||||
end
 | 
					end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					-- Use a prompt coroutine to get git status in the background.
 | 
				
			||||||
 | 
					-- Cache the info so we can reuse it next time to reduce flicker.
 | 
				
			||||||
 | 
					---
 | 
				
			||||||
 | 
					local function get_git_info_table()
 | 
				
			||||||
 | 
					    local info = clink_promptcoroutine(function ()
 | 
				
			||||||
 | 
					        return { status=get_git_status(), conflict=get_git_conflict() }
 | 
				
			||||||
 | 
					    end)
 | 
				
			||||||
 | 
					    if not info then
 | 
				
			||||||
 | 
					        info = cached_info.git_info or {}
 | 
				
			||||||
 | 
					    else
 | 
				
			||||||
 | 
					        cached_info.git_info = info
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					    return info
 | 
				
			||||||
 | 
					end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
---
 | 
					---
 | 
				
			||||||
-- Get the status of working dir
 | 
					-- Get the status of working dir
 | 
				
			||||||
-- @return {bool}
 | 
					-- @return {bool}
 | 
				
			||||||
---
 | 
					---
 | 
				
			||||||
local function get_git_status_setting()
 | 
					local function get_git_status_setting()
 | 
				
			||||||
 | 
					    -- When async prompt filtering is available, check the
 | 
				
			||||||
 | 
					    -- prompt_overrideGitStatusOptIn config setting for whether to ignore the
 | 
				
			||||||
 | 
					    -- cmder.status and cmder.cmdstatus git config opt-in settings.
 | 
				
			||||||
 | 
					    if clink.promptcoroutine and io.popenyield and settings.get("prompt.async") then
 | 
				
			||||||
 | 
					        if prompt_overrideGitStatusOptIn then
 | 
				
			||||||
 | 
					            return true
 | 
				
			||||||
 | 
					        end
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    local gitStatusConfig = io.popen("git --no-pager config cmder.status 2>nul")
 | 
					    local gitStatusConfig = io.popen("git --no-pager config cmder.status 2>nul")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    for line in gitStatusConfig:lines() do
 | 
					    for line in gitStatusConfig:lines() do
 | 
				
			||||||
@@ -392,6 +452,11 @@ end
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
local function git_prompt_filter()
 | 
					local function git_prompt_filter()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    -- Don't do any git processing if the prompt doesn't want to show git info.
 | 
				
			||||||
 | 
					    if not clink.prompt.value:find("{git}") then
 | 
				
			||||||
 | 
					        return false
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    -- Colors for git status
 | 
					    -- Colors for git status
 | 
				
			||||||
    local colors = {
 | 
					    local colors = {
 | 
				
			||||||
        clean = get_clean_color(),
 | 
					        clean = get_clean_color(),
 | 
				
			||||||
@@ -406,15 +471,26 @@ local function git_prompt_filter()
 | 
				
			|||||||
    if git_dir then
 | 
					    if git_dir then
 | 
				
			||||||
        local branch = get_git_branch(git_dir)
 | 
					        local branch = get_git_branch(git_dir)
 | 
				
			||||||
        if branch then
 | 
					        if branch then
 | 
				
			||||||
 | 
					            -- If in a different repo or branch than last time, discard cached info.
 | 
				
			||||||
 | 
					            if cached_info.git_dir ~= git_dir or cached_info.git_branch ~= branch then
 | 
				
			||||||
 | 
					                cached_info.git_info = nil
 | 
				
			||||||
 | 
					                cached_info.git_dir = git_dir
 | 
				
			||||||
 | 
					                cached_info.git_branch = branch
 | 
				
			||||||
 | 
					            end
 | 
				
			||||||
 | 
					            -- Use git status if allowed.
 | 
				
			||||||
            if cmderGitStatusOptIn then
 | 
					            if cmderGitStatusOptIn then
 | 
				
			||||||
                -- if we're inside of git repo then try to detect current branch
 | 
					                -- if we're inside of git repo then try to detect current branch
 | 
				
			||||||
                -- Has branch => therefore it is a git folder, now figure out status
 | 
					                -- Has branch => therefore it is a git folder, now figure out status
 | 
				
			||||||
                local gitStatus = get_git_status()
 | 
					                local gitInfo = get_git_info_table()
 | 
				
			||||||
                local gitConflict = get_git_conflict()
 | 
					                local gitStatus = gitInfo.status
 | 
				
			||||||
 | 
					                local gitConflict = gitInfo.conflict
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                color = colors.dirty
 | 
					                if gitStatus == nil then
 | 
				
			||||||
                if gitStatus then
 | 
					                    color = colors.nostatus
 | 
				
			||||||
 | 
					                elseif gitStatus then
 | 
				
			||||||
                    color = colors.clean
 | 
					                    color = colors.clean
 | 
				
			||||||
 | 
					                else
 | 
				
			||||||
 | 
					                    color = colors.dirty
 | 
				
			||||||
                end
 | 
					                end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
                if gitConflict then
 | 
					                if gitConflict then
 | 
				
			||||||
@@ -435,6 +511,11 @@ end
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
local function hg_prompt_filter()
 | 
					local function hg_prompt_filter()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    -- Don't do any hg processing if the prompt doesn't want to show hg info.
 | 
				
			||||||
 | 
					    if not clink.prompt.value:find("{hg}") then
 | 
				
			||||||
 | 
					        return false
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    local result = ""
 | 
					    local result = ""
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    local hg_dir = get_hg_dir()
 | 
					    local hg_dir = get_hg_dir()
 | 
				
			||||||
@@ -474,6 +555,12 @@ local function hg_prompt_filter()
 | 
				
			|||||||
end
 | 
					end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
local function svn_prompt_filter()
 | 
					local function svn_prompt_filter()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    -- Don't do any svn processing if the prompt doesn't want to show svn info.
 | 
				
			||||||
 | 
					    if not clink.prompt.value:find("{svn}") then
 | 
				
			||||||
 | 
					        return false
 | 
				
			||||||
 | 
					    end
 | 
				
			||||||
 | 
					
 | 
				
			||||||
    -- Colors for svn status
 | 
					    -- Colors for svn status
 | 
				
			||||||
    local colors = {
 | 
					    local colors = {
 | 
				
			||||||
        clean = get_clean_color(),
 | 
					        clean = get_clean_color(),
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										9
									
								
								vendor/cmder_prompt_config.lua.default
									
									
									
									
										vendored
									
									
								
							
							
						
						
									
										9
									
								
								vendor/cmder_prompt_config.lua.default
									
									
									
									
										vendored
									
									
								
							@@ -29,6 +29,15 @@ prompt_useUserAtHost = false
 | 
				
			|||||||
 -- default is false
 | 
					 -- default is false
 | 
				
			||||||
prompt_singleLine = false
 | 
					prompt_singleLine = false
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					-- OPTIONAL. If true then always ignore the cmder.status and cmder.cmdstatus git config settings and run the git prompt commands in the background.
 | 
				
			||||||
 | 
					 -- default is false
 | 
				
			||||||
 | 
					 -- NOTE: This only takes effect if using Clink v1.2.10 or higher.
 | 
				
			||||||
 | 
					prompt_overrideGitStatusOptIn = false
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					-- OPTIONAL. If true then Cmder includes git, mercurial, and subversion status in the prompt.
 | 
				
			||||||
 | 
					 -- default is true
 | 
				
			||||||
 | 
					prompt_includeVersionControl = true
 | 
				
			||||||
 | 
					
 | 
				
			||||||
-- Prompt Attributes
 | 
					-- Prompt Attributes
 | 
				
			||||||
--
 | 
					--
 | 
				
			||||||
-- Colors
 | 
					-- Colors
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user