Don't show add executable and symlink if we just added either of both
[TortoiseGit.git] / src / TortoiseProc / ProgressCommands / AddProgressCommand.cpp
blob3155c1f35742df148ecc0e3148a4e01c7d3d2d74
1 // TortoiseGit - a Windows shell extension for easy version control
3 // Copyright (C) 2011-2016, 2018-2019 - TortoiseGit
5 // This program is free software; you can redistribute it and/or
6 // modify it under the terms of the GNU General Public License
7 // as published by the Free Software Foundation; either version 2
8 // of the License, or (at your option) any later version.
10 // This program is distributed in the hope that it will be useful,
11 // but WITHOUT ANY WARRANTY; without even the implied warranty of
12 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 // GNU General Public License for more details.
15 // You should have received a copy of the GNU General Public License
16 // along with this program; if not, write to the Free Software Foundation,
17 // 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
19 #include "stdafx.h"
20 #include "AddProgressCommand.h"
21 #include "ShellUpdater.h"
22 #include "MassiveGitTask.h"
23 #include "AppUtils.h"
25 bool AddProgressCommand::Run(CGitProgressList* list, CString& sWindowTitle, int& m_itemCountTotal, int& m_itemCount)
27 ATLASSERT(!(m_bExecutable && m_bSymlink));
28 list->SetWindowTitle(IDS_PROGRS_TITLE_ADD, g_Git.CombinePath(m_targetPathList.GetCommonRoot().GetUIPathString()), sWindowTitle);
29 list->SetBackgroundImage(IDI_ADD_BKG);
30 if (m_bExecutable)
31 list->ReportCmd(CString(MAKEINTRESOURCE(IDS_STATUSLIST_CONTEXT_ADD_EXE)));
32 else if (m_bSymlink)
33 list->ReportCmd(CString(MAKEINTRESOURCE(IDS_STATUSLIST_CONTEXT_ADD_LINK)));
34 else
35 list->ReportCmd(CString(MAKEINTRESOURCE(IDS_PROGRS_CMD_ADD)));
37 m_itemCountTotal = m_targetPathList.GetCount();
39 if (g_Git.UsingLibGit2(CGit::GIT_CMD_ADD))
41 CAutoRepository repo(g_Git.GetGitRepository());
42 if (!repo)
44 list->ReportGitError();
45 return false;
48 CAutoIndex index;
49 if (git_repository_index(index.GetPointer(), repo))
51 list->ReportGitError();
52 return false;
54 if (git_index_read(index, true))
56 list->ReportGitError();
57 return false;
60 for (m_itemCount = 0; m_itemCount < m_itemCountTotal; ++m_itemCount)
62 CStringA filePathA = CUnicodeUtils::GetMulti(m_targetPathList[m_itemCount].GetGitPathString(), CP_UTF8).TrimRight(L'/');
63 if (git_index_add_bypath(index, filePathA))
65 list->ReportGitError();
66 return false;
69 if (!m_targetPathList[m_itemCount].IsDirectory() && (m_bExecutable || m_bSymlink))
71 auto entry = const_cast<git_index_entry*>(git_index_get_bypath(index, filePathA, 0));
72 if (m_bExecutable)
73 entry->mode = GIT_FILEMODE_BLOB_EXECUTABLE;
74 else if (m_bSymlink)
75 entry->mode = GIT_FILEMODE_LINK;
76 if (git_index_add(index, entry))
78 list->ReportGitError();
79 return false;
83 list->AddNotify(new CGitProgressList::WC_File_NotificationData(m_targetPathList[m_itemCount], CGitProgressList::WC_File_NotificationData::git_wc_notify_add));
85 if (list->IsCancelled() == TRUE)
87 list->ReportUserCanceled();
88 return false;
92 if (git_index_write(index))
94 list->ReportGitError();
95 return false;
98 else
100 CMassiveGitTask mgt(L"add -f");
101 if (!mgt.ExecuteWithNotify(&m_targetPathList, list->m_bCancelled, CGitProgressList::WC_File_NotificationData::git_wc_notify_add, list))
102 return false;
103 if (m_bExecutable)
105 if (!SetFileMode(GIT_FILEMODE_BLOB_EXECUTABLE))
106 return false;
108 else if (m_bSymlink)
110 if (!SetFileMode(GIT_FILEMODE_LINK))
111 return false;
115 CShellUpdater::Instance().AddPathsForUpdate(m_targetPathList);
117 m_PostCmdCallback = [this](DWORD status, PostCmdList& postCmdList)
119 if (status)
120 return;
122 if (m_bShowCommitButtonAfterAdd)
123 postCmdList.emplace_back(IDI_COMMIT, IDS_MENUCOMMIT, []
125 CString sCmd;
126 sCmd.Format(L"/command:commit /path:\"%s\"", (LPCTSTR)g_Git.m_CurrentDir);
127 CAppUtils::RunTortoiseGitProc(sCmd);
129 if (!(m_bExecutable || m_bSymlink))
131 postCmdList.emplace_back(IDI_ADD, IDS_STATUSLIST_CONTEXT_ADD_EXE, [this] {
132 SetFileMode(GIT_FILEMODE_BLOB_EXECUTABLE);
134 postCmdList.emplace_back(IDI_ADD, IDS_STATUSLIST_CONTEXT_ADD_LINK, [this] {
135 SetFileMode(GIT_FILEMODE_LINK);
140 return true;
143 bool AddProgressCommand::SetFileMode(uint32_t mode)
145 CAutoRepository repo(g_Git.GetGitRepository());
146 if (!repo)
148 MessageBox(nullptr, g_Git.GetLibGit2LastErr(L"Could not open repository."), L"TortoiseGit", MB_ICONERROR);
149 return false;
152 CAutoIndex index;
153 if (git_repository_index(index.GetPointer(), repo))
155 MessageBox(nullptr, g_Git.GetLibGit2LastErr(L"Could not get index."), L"TortoiseGit", MB_ICONERROR);
156 return false;
158 if (git_index_read(index, true))
160 MessageBox(nullptr, g_Git.GetLibGit2LastErr(L"Could not read index."), L"TortoiseGit", MB_ICONERROR);
161 return false;
164 for (int i = 0; i < m_targetPathList.GetCount(); ++i)
166 if (m_targetPathList[i].IsDirectory())
167 continue;
168 CStringA filePathA = CUnicodeUtils::GetMulti(m_targetPathList[i].GetGitPathString(), CP_UTF8).TrimRight(L'/');
169 auto entry = const_cast<git_index_entry*>(git_index_get_bypath(index, filePathA, 0));
170 entry->mode = mode;
171 if (git_index_add(index, entry))
173 MessageBox(nullptr, g_Git.GetLibGit2LastErr(L"Could not update index."), L"TortoiseGit", MB_ICONERROR);
174 return false;
178 if (git_index_write(index))
180 MessageBox(nullptr, g_Git.GetLibGit2LastErr(L"Could not write index."), L"TortoiseGit", MB_ICONERROR);
181 return false;
184 return true;