Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

386 lines
11 KiB

  1. /*++
  2. Copyright (c) 1994-2000 Microsoft Corporation
  3. Module Name :
  4. W3PropPage.cpp
  5. Abstract:
  6. IIS Shell extension PropertyPage class implementation
  7. Author:
  8. Sergei Antonov (sergeia)
  9. Project:
  10. Internet Services Manager
  11. Revision History:
  12. --*/
  13. #include "stdafx.h"
  14. #include "W3PropPage.h"
  15. #include "w3ext.h"
  16. #include "PropShellExt.h"
  17. #include "EditAlias.h"
  18. #include "StrFn.h"
  19. #define SZ_SERVER_KEYTYPE _T("IIsWebServer")
  20. /////////////////////////////////////////////////////////////////////////////
  21. // CW3PropPage
  22. LRESULT
  23. CW3PropPage::OnInitDialog(HWND hDlg, LPARAM lParam)
  24. {
  25. // subclass dialog controls
  26. DoDataExchange();
  27. ASSERT(m_pParentExt != NULL);
  28. CMetaEnumerator en(LOCAL_KEY, CMetabasePath(SZ_MBN_WEB));
  29. ASSERT(en.Succeeded());
  30. if (en.Succeeded())
  31. {
  32. DWORD di;
  33. int i = -1;
  34. CString inst;
  35. HRESULT hr = S_OK;
  36. while (SUCCEEDED(hr))
  37. {
  38. if (SUCCEEDED(hr = en.Next(di, inst)))
  39. {
  40. CString cmt;
  41. if (SUCCEEDED(hr = en.QueryValue(MD_SERVER_COMMENT, cmt, NULL, inst)))
  42. {
  43. if (cmt.IsEmpty())
  44. {
  45. cmt.Format(_Module.GetResourceInstance(),
  46. IDS_DEFAULT_SERVER_COMMENT, di);
  47. }
  48. if (CB_ERR != (i = m_servers_list.AddString(cmt)))
  49. {
  50. m_servers_list.SetItemDataPtr(i, StrDup(inst));
  51. }
  52. }
  53. }
  54. }
  55. if (i >= 0)
  56. m_servers_list.SetCurSel(0);
  57. m_ShareThis = 0;
  58. // Fill shares list box for selected server
  59. OnServerChange(0, 0, NULL);
  60. }
  61. return 1;
  62. }
  63. void
  64. CW3PropPage::OnDestroy()
  65. {
  66. ATLTRACE("In OnDestroy handler\n");
  67. // DebugBreak();
  68. }
  69. HRESULT GetKeyNames(CMetaEnumerator& en, std::set<CString>& keys)
  70. {
  71. CString key;
  72. HRESULT hr;
  73. if (SUCCEEDED(hr = en.Next(key)))
  74. {
  75. keys.insert(key);
  76. }
  77. return hr;
  78. }
  79. void
  80. CW3PropPage::OnAdd(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  81. {
  82. CEditAlias dlg;
  83. int index = m_servers_list.GetCurSel();
  84. LPCTSTR p = (LPCTSTR)m_servers_list.GetItemData(index);
  85. dlg.m_instance = p;
  86. p = m_pParentExt->GetPath();
  87. ::StrCpy(dlg.m_path, p);
  88. dlg.m_new = TRUE;
  89. if (p == PathFindFileName(p))
  90. {
  91. /* No file name -- could be root directory like c:\ */
  92. dlg.m_alias[0] = 0;
  93. }
  94. else
  95. {
  96. TCHAR buf[MAX_PATH];
  97. StrCpy(buf, PathFindFileName(p));
  98. PathMakePretty(buf);
  99. StrCpy(dlg.m_alias, buf);
  100. // Now we need to generate unique prompt for this new alias
  101. CMetaEnumerator en(LOCAL_KEY,
  102. CMetabasePath(TRUE, SZ_MBN_WEB, dlg.m_instance, SZ_MBN_ROOT));
  103. ASSERT(en.Succeeded());
  104. if (en.Succeeded())
  105. {
  106. std::set<CString> keys;
  107. if (SUCCEEDED(GetKeyNames(en, keys)) && !keys.empty())
  108. {
  109. int i = 0;
  110. while (keys.find(buf) != keys.end())
  111. {
  112. wsprintf(buf, _T("%s%d"), dlg.m_alias, ++i);
  113. }
  114. StrCpy(dlg.m_alias, buf);
  115. }
  116. }
  117. }
  118. if (IDOK == dlg.DoModal())
  119. {
  120. OnServerChange(0, 0, NULL);
  121. ::SendMessage(GetParent(), PSM_CHANGED, (WPARAM)m_hWnd, 0);
  122. }
  123. }
  124. void
  125. CW3PropPage::OnRemove(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  126. {
  127. CString cap, msg;
  128. int index = m_servers_list.GetCurSel();
  129. LPCTSTR p = (LPCTSTR)m_servers_list.GetItemData(index);
  130. cap.LoadString(_Module.GetResourceInstance(), IDS_PAGE_TITLE);
  131. index = m_share_list.GetCurSel();
  132. TCHAR buf[MAX_PATH];
  133. m_share_list.GetText(index, buf);
  134. msg.Format(_Module.GetResourceInstance(), IDS_CONFIRM_REMOVE, buf);
  135. CError err;
  136. if (IDYES == MessageBox(msg, cap, MB_YESNO|MB_ICONQUESTION))
  137. {
  138. CWaitCursor wait;
  139. do
  140. {
  141. CIISApplication app(NULL, CMetabasePath(TRUE, SZ_MBN_WEB, p, SZ_MBN_ROOT, buf));
  142. err = app.QueryResult();
  143. BREAK_ON_ERR_FAILURE(err)
  144. err = app.Delete(TRUE);
  145. } while (FALSE);
  146. if (err.Succeeded())
  147. {
  148. CMetaKey mk(LOCAL_KEY,
  149. CMetabasePath(TRUE, SZ_MBN_WEB, p, SZ_MBN_ROOT),
  150. METADATA_PERMISSION_WRITE);
  151. err = mk.DeleteKey(buf);
  152. if (err.Succeeded())
  153. {
  154. m_share_list.DeleteString(index);
  155. int count = m_share_list.GetCount();
  156. m_ShareThis = count > 0 ? 1 : 0;
  157. if (m_ShareThis)
  158. {
  159. m_share_list.SetCurSel(index >= count ? count - 1 : index);
  160. }
  161. EnableOnShare();
  162. CheckDlgButton(IDC_SHARE_ON, m_ShareThis);
  163. CheckDlgButton(IDC_SHARE_OFF, !m_ShareThis);
  164. ::SendMessage(GetParent(), PSM_CHANGED, (WPARAM)m_hWnd, 0);
  165. }
  166. else
  167. {
  168. err.MessageBox();
  169. }
  170. }
  171. else
  172. {
  173. err.MessageBox();
  174. }
  175. }
  176. }
  177. void
  178. CW3PropPage::OnEdit(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  179. {
  180. CEditAlias dlg;
  181. int index = m_servers_list.GetCurSel();
  182. LPCTSTR p = (LPCTSTR)m_servers_list.GetItemData(index);
  183. dlg.m_instance = p;
  184. p = m_pParentExt->GetPath();
  185. ::StrCpy(dlg.m_path, p);
  186. index = m_share_list.GetCurSel();
  187. TCHAR buf[MAX_PATH];
  188. m_share_list.GetText(index, buf);
  189. ::StrCpy(dlg.m_alias, buf);
  190. dlg.m_new = FALSE;
  191. if (IDOK == dlg.DoModal())
  192. {
  193. OnServerChange(0, 0, NULL);
  194. ::SendMessage(GetParent(), PSM_CHANGED, (WPARAM)m_hWnd, 0);
  195. }
  196. }
  197. void
  198. CW3PropPage::OnServerChange(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  199. {
  200. // get selected server instance number
  201. int index = m_servers_list.GetCurSel();
  202. if (LB_ERR != index)
  203. {
  204. LPTSTR p = (LPTSTR)m_servers_list.GetItemDataPtr(index);
  205. CMetabasePath path(TRUE, SZ_MBN_WEB, p, SZ_MBN_ROOT);
  206. CMetaEnumerator en(LOCAL_KEY, path);
  207. ASSERT(en.Succeeded());
  208. m_share_list.ResetContent();
  209. if (en.Succeeded())
  210. {
  211. RecurseVDirs(en, NULL);
  212. }
  213. m_ShareThis = m_share_list.GetCount() > 0 ? 1 : 0;
  214. }
  215. if (m_ShareThis)
  216. {
  217. m_share_list.SetCurSel(0);
  218. }
  219. EnableOnShare();
  220. CheckDlgButton(IDC_SHARE_ON, m_ShareThis);
  221. CheckDlgButton(IDC_SHARE_OFF, !m_ShareThis);
  222. ::SendMessage(GetParent(), PSM_CHANGED, (WPARAM)m_hWnd, 0);
  223. }
  224. void
  225. CW3PropPage::RecurseVDirs(CMetaEnumerator& en, LPCTSTR path)
  226. {
  227. CString vrpath, csPathMunged;
  228. BOOL bInheritOverride = FALSE;
  229. if (SUCCEEDED(en.QueryValue(MD_VR_PATH, vrpath, &bInheritOverride, path)))
  230. {
  231. GetSpecialPathRealPath(vrpath,csPathMunged);
  232. if (csPathMunged.CompareNoCase(m_pParentExt->GetPath()) == 0)
  233. {
  234. CMetabasePath mpath(FALSE, path);
  235. CMetabasePath::CleanMetaPath(mpath);
  236. m_share_list.AddString(path == NULL ?
  237. SZ_MBN_SEP_STR : mpath.QueryMetaPath());
  238. }
  239. }
  240. CString vdir;
  241. while (SUCCEEDED(en.Next(vdir, path)))
  242. {
  243. CString next_vdir;
  244. if (path != NULL)
  245. next_vdir += path;
  246. next_vdir += vdir;
  247. next_vdir += SZ_MBN_SEP_STR;
  248. en.Push();
  249. en.Reset();
  250. RecurseVDirs(en, next_vdir);
  251. en.Pop();
  252. }
  253. }
  254. void
  255. CW3PropPage::OnShareYesNo(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  256. {
  257. int count = m_share_list.GetCount();
  258. m_ShareThis = IsDlgButtonChecked(IDC_SHARE_ON);
  259. if (m_ShareThis)
  260. {
  261. if (count <= 0)
  262. {
  263. OnAdd(0, 0, NULL);
  264. m_ShareThis = (m_share_list.GetCount() > 0);
  265. }
  266. }
  267. else
  268. {
  269. if (count > 0)
  270. {
  271. CString cap, msg;
  272. int index = m_servers_list.GetCurSel();
  273. LPCTSTR p = (LPCTSTR)m_servers_list.GetItemData(index);
  274. cap.LoadString(_Module.GetResourceInstance(), IDS_PAGE_TITLE);
  275. msg.LoadString(_Module.GetResourceInstance(), IDS_CONFIRM_REMOVE_ALL);
  276. CError err;
  277. if (IDYES == MessageBox(msg, cap, MB_YESNO))
  278. {
  279. CWaitCursor wait;
  280. TCHAR alias[MAX_PATH];
  281. int del_idx = 0;
  282. for (index = 0; err.Succeeded() && index < count; index++)
  283. {
  284. m_share_list.GetText(del_idx, alias);
  285. if (0 == StrCmp(alias, SZ_MBN_SEP_STR))
  286. {
  287. // Do not remove sites! Skip it.
  288. del_idx++;
  289. continue;
  290. }
  291. do
  292. {
  293. CIISApplication app(NULL, CMetabasePath(TRUE, SZ_MBN_WEB, p, SZ_MBN_ROOT, alias));
  294. err = app.QueryResult();
  295. BREAK_ON_ERR_FAILURE(err)
  296. err = app.Delete(TRUE);
  297. BREAK_ON_ERR_FAILURE(err)
  298. CMetaKey mk(LOCAL_KEY,
  299. CMetabasePath(TRUE, SZ_MBN_WEB, p, SZ_MBN_ROOT),
  300. METADATA_PERMISSION_WRITE);
  301. err = mk.DeleteKey(alias);
  302. BREAK_ON_ERR_FAILURE(err)
  303. } while (FALSE);
  304. BREAK_ON_ERR_FAILURE(err)
  305. m_share_list.DeleteString(del_idx);
  306. }
  307. if (err.Failed() || del_idx > 0)
  308. {
  309. // BUGBUG: we have AV when preparing message box text here
  310. // err.MessageBox();
  311. m_ShareThis = TRUE;
  312. }
  313. }
  314. else
  315. {
  316. m_ShareThis = TRUE;
  317. }
  318. }
  319. }
  320. CheckDlgButton(IDC_SHARE_ON, m_ShareThis);
  321. CheckDlgButton(IDC_SHARE_OFF, !m_ShareThis);
  322. EnableOnShare();
  323. ::SendMessage(GetParent(), PSM_CHANGED, (WPARAM)m_hWnd, 0);
  324. }
  325. void
  326. CW3PropPage::EnableOnShare()
  327. {
  328. m_share_list.EnableWindow(m_ShareThis);
  329. ::EnableWindow(GetDlgItem(IDC_ADD), m_ShareThis);
  330. ::EnableWindow(GetDlgItem(IDC_EDIT), m_ShareThis
  331. && m_share_list.GetCurSel() != LB_ERR);
  332. ::EnableWindow(GetDlgItem(IDC_REMOVE), m_ShareThis
  333. && m_share_list.GetCurSel() != LB_ERR);
  334. if (m_ShareThis)
  335. {
  336. EnableEditRemove();
  337. }
  338. }
  339. void
  340. CW3PropPage::OnVDirChange(WORD wNotifyCode, WORD wID, HWND hWndCtl)
  341. {
  342. EnableEditRemove();
  343. }
  344. void
  345. CW3PropPage::EnableEditRemove()
  346. {
  347. // We are disabling Edit and Remove buttons when user
  348. // select root alias, i.e. user cannot delete or edit sites
  349. int index = m_share_list.GetCurSel();
  350. BOOL bEnable = index != LB_ERR;
  351. if (bEnable)
  352. {
  353. TCHAR alias[MAX_PATH];
  354. m_share_list.GetText(index, alias);
  355. bEnable = (0 != StrCmp(alias, SZ_MBN_SEP_STR));
  356. }
  357. ::EnableWindow(GetDlgItem(IDC_EDIT), bEnable);
  358. ::EnableWindow(GetDlgItem(IDC_REMOVE), bEnable);
  359. }