- 更新 .gitignore 文件,添加便携版分发目录和 Fody 生成的配置文件。 - 修改 README.md,详细说明便携版的构建与分发流程,强调单文件分发的优势。 - 在 Config.cs 中实现便携配置管理,优先使用 exe 同目录的 config.json,提升用户体验。 - 更新 ExcelService.cs,优化默认模板的导出逻辑,支持现场替换模板文件。 - 在 MainForm.cs 中加载应用图标,提升界面一致性。 - 调整 Program.cs,确保在单文件分发时正确加载 native DLL。
124 lines
4.5 KiB
C#
124 lines
4.5 KiB
C#
using System;
|
|
using System.IO;
|
|
using Newtonsoft.Json;
|
|
|
|
namespace TfsExcelImporter
|
|
{
|
|
/// <summary>
|
|
/// 程序配置。保存于 exe 同目录 config.json,界面修改后自动写回。
|
|
/// </summary>
|
|
public class AppConfig
|
|
{
|
|
public string TfsUrl { get; set; } = "http://pdtfs01.dev.goldenstand.cn:8080/tfs/DefaultCollection";
|
|
public string Project { get; set; } = "Tools_Dev";
|
|
public string WorkItemType { get; set; } = "Task";
|
|
|
|
// 目标迭代:完整迭代路径,如 Tools_Dev\2026年Sprint\2026年Sprint10
|
|
public string IterationPath { get; set; } = "";
|
|
// 可选:区域路径
|
|
public string AreaPath { get; set; } = "";
|
|
|
|
// ntlm | basic | default(当前 Windows 凭据)
|
|
public string AuthMode { get; set; } = "ntlm";
|
|
public string Username { get; set; } = "";
|
|
public string Password { get; set; } = "";
|
|
public string Domain { get; set; } = "";
|
|
|
|
// 是否走 IE 系统代理。内网 TFS 请保持 false(直连);
|
|
// 代理/网关常对 HttpClient 请求返回 502(浏览器例外名单直连,.NET 不一定继承)
|
|
public bool UseSystemProxy { get; set; } = false;
|
|
|
|
public bool BypassRules { get; set; } = true;
|
|
public bool SkipExistingTitles { get; set; } = true;
|
|
public string DefaultState { get; set; } = "To Do";
|
|
|
|
// 自定义字段引用名;留空则按 DisplayName 自动解析
|
|
public string FinancialProjectRef { get; set; } = "";
|
|
public string CompletedRef { get; set; } = "";
|
|
public string LogDateRef { get; set; } = "";
|
|
// Original Estimate 导入时取 Completed 的值;引用名留空则按显示名解析
|
|
public string OriginalEstimateRef { get; set; } = "";
|
|
|
|
public string LastExcelPath { get; set; } = "";
|
|
|
|
// 父 Product Backlog Item:所有 Task 默认挂接的 PBI Id(如 219975);Excel 每行 PBI Id 列可覆盖
|
|
public string ParentPbiId { get; set; } = "";
|
|
|
|
// 便携优先:配置写在 exe 同目录(拷走 exe 即可带走配置);
|
|
// exe 目录只读(如放在 Program Files)时回退到 %AppData%\TfsExcelImporter。
|
|
private static string PortableConfigPath
|
|
{
|
|
get { return Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "config.json"); }
|
|
}
|
|
|
|
private static string RoamingConfigPath
|
|
{
|
|
get
|
|
{
|
|
return Path.Combine(
|
|
Environment.GetFolderPath(Environment.SpecialFolder.ApplicationData),
|
|
"TfsExcelImporter", "config.json");
|
|
}
|
|
}
|
|
|
|
private static string ConfigPath
|
|
{
|
|
get
|
|
{
|
|
if (File.Exists(PortableConfigPath)) return PortableConfigPath;
|
|
if (File.Exists(RoamingConfigPath)) return RoamingConfigPath;
|
|
return PortableConfigPath;
|
|
}
|
|
}
|
|
|
|
/// <summary>当前实际使用的配置文件路径(界面提示用)。</summary>
|
|
public static string ConfigLocation
|
|
{
|
|
get { return ConfigPath; }
|
|
}
|
|
|
|
public static AppConfig Load()
|
|
{
|
|
try
|
|
{
|
|
if (File.Exists(ConfigPath))
|
|
{
|
|
var cfg = JsonConvert.DeserializeObject<AppConfig>(File.ReadAllText(ConfigPath));
|
|
if (cfg != null) return cfg;
|
|
}
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
System.Diagnostics.Debug.WriteLine("读取 config.json 失败: " + ex.Message);
|
|
}
|
|
return new AppConfig();
|
|
}
|
|
|
|
public void Save()
|
|
{
|
|
var json = JsonConvert.SerializeObject(this, Formatting.Indented);
|
|
try
|
|
{
|
|
File.WriteAllText(ConfigPath, json);
|
|
return;
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
System.Diagnostics.Debug.WriteLine("写入 config.json 失败: " + ex.Message);
|
|
}
|
|
|
|
// exe 目录不可写(只读介质 / Program Files)时落到用户配置目录
|
|
try
|
|
{
|
|
var fallback = RoamingConfigPath;
|
|
Directory.CreateDirectory(Path.GetDirectoryName(fallback));
|
|
File.WriteAllText(fallback, json);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
System.Diagnostics.Debug.WriteLine("写入用户配置目录失败: " + ex.Message);
|
|
}
|
|
}
|
|
}
|
|
}
|