解决方案看起来是受源代码管理,但无法找到它的帮定信息.保存解决方案的源代码管理设置的MSSCCPRJ.SCC文件或其他项可能己被删除.由于无法自动恢复这些缺少的信息,缺少帮定的项目将被视为不受源代码管理.

“解决方案看起来是受源代码管理,但无法找到它的帮定信息.保存解决方案的源代码管理设置的MSSCCPRJ.SCC文件或其他项可能己被删除.由于无法自动恢复这些缺少的信息,缺少帮定的项目将被视为不受源代码管理.”
 
 
     从网上,或者光盘 copy 来的代码 打开时总会出现这种问题
具体的原因:
     它的开发小组在开发过程中使用了VSS(Visual Source Safe)来进行团队协作,而你的机器上没有这些信息
 
看到有人提供了一种好的方法:
用C#去除代码的SourceSafe管理
经常看一些的程序,有些一个解决方案带有多个项目,由于代码比较多,多人开发,所以好多vs.net下的工程是用source safe进行版本控制的。而用source safe进行版本控制需要局域网路径共享,因此好多项目换一台机器打开会出现一些问题,比如“解决方案看起来是受源代码管理,但无法找到它的绑定信息……”之类的提示信息很多。有时候修改了代码还保存不了,所以想把他去掉,下面是对项目管理前后的一些对比。


一、工程项目比较

同没有受Source Safe代码管理的工程相比:

1.   多出了.scc、.vssscc和.vspscc文件;

2.   C#项目文件(.csproj)里面添加了几行标签:

SccProjectName = "SAK"

SccLocalPath = "SAK"

SccAuxPath = "SAK"

SccProvider = "SAK"

3.在解决方案文件(.sln)中,中增加了如下节点原素:

         GlobalSection(SourceCodeControl) = preSolution

                   SccNumberOfProjects = 4

                   SccLocalPath0 = .

                   ……

SccLocalPath3 = SUBSCRIBE_TOOLS

                   CanCheckoutShared = false

         EndGlobalSection



二、编写实现的类

既然文件增多了,还有有些文件被修改,所以想通过编程把他修改回原样,这样可能可以去掉那些提示信息,所以就写了下面的代码。


//**********************************************************

// 功能:去除C#.net的原代码Source safe 管理

//**********************************************************

using System;

using System.IO;

using System.Text;

using System.Threading;

namespace ZZ

{

     /// <summary>

     /// 操作信息事件代理

     /// </summary>

     public delegate void OperateNotifyHandler(object sender,VssEventArgs e);

     /// <summary>

     /// VssConverter 处理解决方案或项目的SourceSafe关联。

     /// </summary>

     public class VssConverter

     {

         //操作根目录

         private string operatePath;

         /// <summary>

         /// 操作信息事件

         /// </summary>

         public event OperateNotifyHandler OperateNotify;

         /// <summary>

         /// 线程结束通知事件

         /// </summary>

         public event EventHandler ThreadCompleted;

         /// <summary>

         /// 构造函数

         /// </summary>

         /// <param name="operatePath">项目路径</param>

         public VssConverter(string operatePath)

         {

              this.operatePath = operatePath;

         }

     OperatePath属性,用来设置或获取当前需要处理的工程路径,不过在运行时最好不要设置他,


         /// <summary>

         /// 设置解决方案工程路径

         /// </summary>

         public string OperatePath

         {

              get{return this.operatePath;}

              set{this.operatePath = value;}

         }

     下面是一个public 修饰符的函数,也是类实例的惟一对外公开的方法,里面用了两个线程来分别删除文件和修改文件。


         /// <summary>

         /// 去除Source Safe代码管理

         /// </summary>

         public void RemoveVss()

         {

              Thread deleteThread = new Thread(new ThreadStart(DeleteVssFile));

              Thread RemoveVssIdentifyThread = new Thread(new ThreadStart(RemoveVssIdentify));

              deleteThread.Start();

              RemoveVssIdentifyThread.Start();

         }

后来测试了一下deleteThread的完成要比RemoveVssIdentifyThread快一些,当然也可以再开一个线程来分担文件的修改,不过这里需要注意的是好多文件是带只读属性的,所以还要把文件属性设置成Normal才能顺利完成操作,否则会抛出异常。

这里使用了递归来删除相关文件,由三个函数构成:


         /// <summary>

         /// 线程委托函数,完成删除"*.scc","*.vssscc"以及*.vspscc文件功能。

         /// </summary>

         private void DeleteVssFile()

         {

              DeleteVssFile(this.operatePath);

              //通知删除文件结束

              OnThreadCompleted(this,new EventArgs());

         }

         /// <summary>

         ///  递归函数,删除"*.scc","*.vssscc"以及*.vspscc文件。

         /// </summary>

         /// <param name="path">当前处理路径</param>

         private void DeleteVssFile(string path)

         {

              DeleteFile(Directory.GetFiles(path,"*.scc"));

              DeleteFile(Directory.GetFiles(path,"*.vssscc"));

              DeleteFile(Directory.GetFiles(path,"*.vspscc"));

              foreach(string dir in Directory.GetDirectories(path))

                   DeleteVssFile(dir);

         }

         /// <summary>

         /// 删除文件,真正删除文件

         /// </summary>

         /// <param name="files"></param>

         private void DeleteFile(string [] files)

         {

              foreach(string file in files)

              {

                   FileInfo fi = new FileInfo(file);

                   fi.Attributes = FileAttributes.Normal;

                   File.Delete(file);

                   OnOperateNotify(this,new VssEventArgs(file+"删除完成"));

              }

         }

对于".sln"解决方案文件和".csproj’"C#项目文件的修改也采用了递归实现:


                   /// <summary>

         /// 线程委托函数,去除"*.sln"解决方案文件和"*.csproj"C#项目文件的.Vss关联标签。

         /// </summary>

         private void RemoveVssIdentify()

         {

              RemoveVssTag(this.operatePath);

              //通知去除标签结束

              OnThreadCompleted(this,new EventArgs());

         }

        

         /// <summary>

         /// 去除"*.sln"解决方案文件和"*.csproj"C#项目文件的.Vss关联标签。

         /// </summary>

         /// <param name="path">当前处理路径</param>

         private void RemoveVssTag(string path)

         {

              RemoveTagContent(Directory.GetFiles(path,"*.sln"));

              RemoveTagContent(Directory.GetFiles(path,"*.csproj"));

              foreach(string dir in Directory.GetDirectories(path))

                   RemoveVssTag(dir);

         }

     下面的函数用来分析处理文件的修改,因为都是做删除部分文件内容的工作,所以把处理函数写成了一个,


         /// <summary>

         /// 去除"*.sln"解决方案文件和"*.csproj"C#项目文件的.Vss关联标签。

         /// </summary>

         /// <param name="file">当前处理文件</param>

         private void RemoveTagContent(string [] files)

         {

              foreach(string file in files)

              {

                   string strStart; //Vss标签文本开始内容

                   string strEnd; //标签文本结束内容

                   int offSet;//结束标签文本的偏移量

                   FileInfo fi = new FileInfo(file);

                   fi.Attributes =FileAttributes.Normal;

                   if(fi.Extension == ".sln")//如果是解决方案文件

                   {

                       strStart = "GlobalSection(SourceCodeControl)";

                       strEnd = "EndGlobalSection";

                       offSet = 19;//包含/r/n和空格

                   }

                   else//如果是项目文件

                   {

                       strStart = "SccProjectName";

                       strEnd = ">";

                       offSet = 0;

                   }

                   try

                   {

                       int start;//Vss标签文本开始索引

                       int end;//Vss标签文本结束索引

                       string content;//文件内容

                       using(FileStream fs = new FileStream(file,FileMode.Open,FileAccess.ReadWrite,FileShare.ReadWrite))

                       {

                            StreamReader sr = new StreamReader(fs);

                            content = sr.ReadToEnd();

                            sr.Close();

                            start = content.IndexOf(strStart);

                       }

                       if(start!=-1)//文件需要去除标签

                       {

                            using(FileStream fs = new FileStream(file,FileMode.Truncate,FileAccess.Write,FileShare.Read))

                            {

                                 end = start+content.Substring(start).IndexOf(strEnd)+offSet;

                                 content = content.Substring(0,start)+content.Substring(end);

                                 StreamWriter sw = new StreamWriter(fs);

                                 sw.Write(content);

                                 sw.Close();

                            }

                            OnOperateNotify(this,new VssEventArgs(file+"去除标签完成"));

                       }

                   }

                   catch(Exception ex)

                   {

                       OnOperateNotify(this,new VssEventArgs(file+"操作错误:"+ex.ToString()));

                   }

              }            

     }

当此为止,上面的程序实现了主要的功能,不过上面定义的事件,下面就是关于事件的函数,


         /// <summary>

         /// 操作信息事件通知

         /// </summary>

         /// <param name="sender">VssConverter</param>

         /// <param name="e">参数,</param>

         protected virtual void OnOperateNotify(object sender,VssEventArgs e)

         {

              if(OperateNotify!=null)

                   OperateNotify(sender,e);

         }

         /// <summary>

         /// 线程结束事件通知

         /// </summary>

         /// <param name="sender">VssConverter</param>

         /// <param name="e">参数</param>

         protected virtual void OnThreadCompleted(object sender,EventArgs e)

         {

              if(ThreadCompleted!=null)

                   ThreadCompleted(sender,e);

     }

}

相对于事件中的参数,这里定义了一个类从EventArgs继承,里面只包含一个字段用来保存信息,


/// <summary>

     /// 消息通知事件参数类

     /// </summary>

     public class VssEventArgs : EventArgs

     {

         private string message;

         /// <summary>

         /// 构造函数

         /// </summary>

         /// <param name="message"></param>

         public VssEventArgs(string message)

         {

              this.message = message;

         }

         /// <summary>

         /// 消息内容

         /// </summary>

         public string Message

         {

              get{return this.message;}

         }

}

}//命名空间
 
 
三、测试使用

程序测试运行界面,


界面部分代码大多数由设计器生成,下面列出了主要添加代码,


//委托,更新文本框

private delegate void AppendTextHandler(string content);

//标记转换操作是否完成

private int convertOK =0;

private System.Windows.Forms.TextBox textBoxFolder;//路径文本框

private System.Windows.Forms.Button buttonFolder;//浏览按钮

private System.Windows.Forms.TextBox textBoxInfo;//信息显示框

private System.Windows.Forms.Button buttonOK;//运行按钮

private System.Windows.Forms.Button buttonCancel;//退出按钮

按钮处理函数用来打开一个路径选择框,

private void buttonFolder_Click(object sender, System.EventArgs e)

{

     FolderBrowserDialog myDialog = new  FolderBrowserDialog();

     myDialog.ShowNewFolderButton = false;

     myDialog.Description = "选择需要处理的解决方案或项目目录";

     if(myDialog.ShowDialog()==DialogResult.OK)

         this.textBoxFolder.Text = myDialog.SelectedPath;

     myDialog.Dispose();

}

运行函数,在这里面实例化VssConverter类,并调用了RemoveVss方法,运行时把几个按钮禁了,里面注册了两个事件,起信息传递作用,不过对于直接在地址栏中输入非法路径没有做具体判断,

private void buttonOK_Click(object sender, System.EventArgs e)

{

     if(this.textBoxFolder.Text.Length>1)

     {

         this.textBoxInfo.Clear();

         this.convertOK = 0;

         this.buttonOK.Enabled = false;

         this.buttonFolder.Enabled = false;

         this.buttonCancel.Enabled = false;

         this.textBoxFolder.Enabled = false;

         VssConverter vssConverter = new VssConverter(this.textBoxFolder.Text);

         vssConverter.OperateNotify += new OperateNotifyHandler(vssConverter_OperateNotify);

         vssConverter.ThreadCompleted += new EventHandler(vssConverter_ThreadCompleted);

         vssConverter.RemoveVss();

     }

     else

         MessageBox.Show("请输入解决方案或项目路径!");

}

下面是两个事件处理函数,第一个是用来在前台即时显示当前处理的文件信息,第二个函数是用来通知线程的执行结果。函数如下,

// 信息通知

private void vssConverter_OperateNotify(object sender, VssEventArgs e)

{

     AppendTextHandler ath = new AppendTextHandler(this.textBoxInfo.AppendText);

     this.textBoxInfo.BeginInvoke(ath,new object[]{e.Message+Environment.NewLine});

}

// 线程结束通知

private void vssConverter_ThreadCompleted(object sender, EventArgs e)

{

     if(this.convertOK==0)

         this.convertOK++;

     else

     {

         this.buttonOK.Enabled = true;

         this.buttonFolder.Enabled = true;

         this.buttonCancel.Enabled = true;

         this.textBoxFolder.Enabled = true;

         this.textBoxInfo.AppendText("#### 转换完成 ####");

     }

### 回答1: VB6是一种老旧的编程语言,不支持自动版本更新的功能。然而,我们可以通过编写代码来实现类似的版本更新处理。 首先,我们可以创建一个版本检查的模块,该模块可以通过与服务器通信来检查是否有新版本可用。可以使用网络库或者简单的HTTP请求来实现与服务器的通信。 在代码中,我们可以编写一个函数来检查可用的最新版本号。该函数可以根据服务器返回的版本号进行比较,并返回一个布尔值,指示是否有新版本可用。 接下来,我们可以在程序启动时调用该函数,以确定是否有新版本可用。如果有新版本,则可以提示用户进行更新,并提供下载链接。 当用户点击下载链接时,我们可以使用Shell函数或者ShellExecute函数在浏览器中打开下载链接。 在下载完成后,我们可以使用文件操作的函数来将新的应用程序文件复制到指定位置,并自动运行更新后的应用程序。 需要注意的是,由于VB6的局限性,自动版本更新处理可能不会像其他现代编程语言一样流畅和高效。因此,在编写代码时,需要注意异常处理和用户体验,并进行充分的测试。 总结起来,虽然VB6不支持自动版本更新功能,但我们可以通过编写代码实现类似的功能。我们可以在程序启动时检查服务器是否有新版本可用,并根据用户选择下载并安装新版本。尽管不如现代编程语言那样便捷,但我们可以通过一些技巧来解决这个问题。 ### 回答2: VB6是一种编程语言,通过它可以开发Windows应用程序。在VB6中实现自动版本更新的处理需要一些额外的代码和逻辑。下面是一个简单的示例源码来演示如何实现VB6的自动版本更新处理。 ```vb ' 声明WinAPI函数 Private Declare Function URLDownloadToFile Lib "urlmon" Alias "URLDownloadToFileA" _ (ByVal pCaller As Long, ByVal szURL As String, ByVal szFileName As String, _ ByVal dwReserved As Long, ByVal lpfnCB As Long) As Long Private Sub Form_Load() ' 检查服务器上的最新版本号 Dim latestVersion As String latestVersion = CheckLatestVersion() ' 检查当前应用程序的版本号 Dim currentVersion As String currentVersion = App.Major & "." & App.Minor & "." & App.Revision ' 比较版本号,如果不相同则进行更新处理 If latestVersion <> currentVersion Then ' 下载最新版本的应用程序文件 Dim url As String url = "http://yourwebsite.com/latest_version.exe" Dim fileName As String fileName = App.Path & "\latest_version.exe" If DownloadFile(url, fileName) Then ' 下载成功,启动最新版本的应用程序 Shell fileName, vbNormalFocus ' 关闭当前版本的应用程序 Unload Me Else ' 下载失败,显示错误提示 MsgBox "下载最新版本失败,请稍后再试。", vbCritical End If End If End Sub Private Function CheckLatestVersion() As String ' 在此处实现与服务器通信,获取最新版本号的逻辑 ' 返回最新版本号 ' 例如,直接返回一个固定的字符串作为演示 CheckLatestVersion = "2.0.0" End Function Private Function DownloadFile(url As String, fileName As String) As Boolean ' 使用URLDownloadToFile函数下载文件 Dim result As Long result = URLDownloadToFile(0, url, fileName, 0, 0) ' 返回下载结果 DownloadFile = (result = 0) End Function ``` 以上代码演示了一个简单的自动版本更新处理的示例。程序首先通过与服务器通信获取最新版本号,然后比较最新版本号与当前版本号是否相同。如果不相同,程序会使用URLDownloadToFile函数从指定URL下载最新版本的应用程序文件,然后启动最新版本的应用程序并关闭当前版本的应用程序。如果下载失败,程序会显示错误提示。 请注意,上述代码只是一个简化的示例,实际情况下可能需要更多的处理和逻辑,例如处理更新过程中的错误、显示下载进度、备份数据等。 ### 回答3: VB6通过使用文件版本控制组件来实现自动版本更新处理。可以使用"MSSCCPRJ.SCCProvider.1"这个组件来实现文件版本控制。下面是一个自动版本更新处理的示例源码: ```vb Private Sub AutoUpdate() ' 设置版本号 Dim version As String version = App.Major & "." & App.Minor & "." & App.Revision ' 定义文件版本控制对象 Dim fso As Object Dim sccProvider As Object ' 创建文件版本控制对象 Set fso = CreateObject("Scripting.FileSystemObject") Set sccProvider = CreateObject("MSSCCPRJ.SCCProvider.1") ' 检查是否有新版本可用 If sccProvider.GetLastVersionNumber("path\to\your\version\control\folder") > version Then ' 下载新版本文件 Dim serverPath As String serverPath = "http://yourserver/updates/version.exe" ' 新版本文件的下载路径 Dim localPath As String localPath = "path\to\the\local\folder" ' 本地保存新版本文件文件夹路径 ' 删除旧版本文件 Dim oldVersionPath As String oldVersionPath = "path\to\the\old\version\file" If fso.FileExists(oldVersionPath) Then fso.DeleteFile oldVersionPath End If ' 下载新版本文件 Dim xmlHTTP As Object Set xmlHTTP = CreateObject("MSXML2.XMLHTTP") xmlHTTP.Open "GET", serverPath, False xmlHTTP.send ' 保存新版本文件 Dim stream As Object Set stream = CreateObject("ADODB.Stream") stream.type = 1 stream.open stream.write xmlHTTP.responseBody stream.saveToFile localPath & "\version.exe", 2 stream.close Set stream = Nothing Set xmlHTTP = Nothing ' 执行新版本文件的更新操作 Shell localPath & "\version.exe" ' 退出当前程序 End End If End Sub ``` 以上就是一个简单的VB6自动版本更新处理的示例源码。在这个示例中,我们通过检查文件版本控制库中是否有新版本可用来实现自动更新。如果有新版本,则下载新版本文件并运行更新操作。最后,退出当前程序,以便新版本能够生效。请根据实际情况修改代码中的文件路径和服务器路径。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值