Graphviz 拓扑图

1. 安装Graphviz 2.28, 安装目录不要修改,C:\Program Files\Graphviz 2.28\bin\dot.exe;

2. 在Web.config中,添加节点:

[csharp] view plain copy
  1. <appSettings>  
  2.   <!-- Graphviz 执行文件路径 -->  
  3.   <add key="dotExePath" value="C:\Program Files\Graphviz 2.28\bin\dot.exe" />  
  4. </appSettings>  

3. 建立帮助类

[csharp] view plain copy
  1. using System;  
  2. using System.Collections.Generic;  
  3. using System.Text.RegularExpressions;  
  4. using System.Web;  
  5. using System.IO;  
  6. using System.Diagnostics;  
  7. using System.Text;  
  8. using System.Net;  
  9. using System.Drawing.Imaging;  
  10. using System.Drawing;  
  11.   
  12. namespace Module.Common  
  13. {  
  14.     /// <summary>  
  15.     /// 拓扑图  
  16.     /// </summary>  
  17.     public class GraphvizHelper  
  18.     {  
  19.         public static void SaveWebImgToLocal(string url)   
  20.         {  
  21.             string path=GetImgSavePath();  
  22.             if(path=="" || url.IndexOf('/')== -1 )  
  23.                 return;  
  24.   
  25.             path += url.Substring(url.LastIndexOf('/'));  
  26.   
  27.             WebClient my=new WebClient();  
  28.             byte[] mybyte;    
  29.             mybyte=my.DownloadData(url);  
  30.             MemoryStream ms = new MemoryStream(mybyte);  
  31.             System.Drawing.Image img = System.Drawing.Image.FromStream(ms);  
  32.             img.Save(path, ImageFormat.Png);   //保存   
  33.             switch (Path.GetExtension(path))  
  34.             {  
  35.                 case ".gif":  
  36.                     img.Save(path, ImageFormat.Gif);  
  37.                     break;  
  38.                 case ".jpg":  
  39.                 case ".jpeg":  
  40.                     img.Save(path, ImageFormat.Jpeg);  
  41.                     break;  
  42.                 case ".png":  
  43.                     img.Save(path, ImageFormat.Png);  
  44.                     break;  
  45.                 case ".icon":  
  46.                     img.Save(path, ImageFormat.Icon);  
  47.                     break;  
  48.                 case ".bmp":  
  49.                     img.Save(path, ImageFormat.Bmp);  
  50.                     break;  
  51.                 default:  
  52.                     img.Save(path, ImageFormat.Png);  
  53.                     break;  
  54.             }  
  55.             img.Dispose();  
  56.             ms.Dispose();  
  57.   
  58.             CompressJpeg(path, 64);  
  59.         }  
  60.   
  61.         public static void CompressJpeg(string strPath, int intWidth)  
  62.         {  
  63.             var img = Image.FromFile(strPath);        // 如果不是图片会出错。  
  64.             if (img.Width <= intWidth)  
  65.             {  
  66.                 img.Dispose();  
  67.                 return;  
  68.             }  
  69.             var intHeight = img.Height * intWidth / img.Width;  
  70.             // 创建位图及相关联的图形处理工具,在位图上画缩略图  
  71.             var thm = new Bitmap(intWidth, intHeight);  
  72.             var grp = Graphics.FromImage(thm);  
  73.             //设置高质量插值法  
  74.             grp.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.High;  
  75.             //设置高质量,低速度呈现平滑程度  
  76.             grp.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;  
  77.             grp.Clear(System.Drawing.Color.Transparent);//清空画布以透明填充  
  78.             grp.DrawImage(img, 0, 0, intWidth, intHeight);  
  79.             // 释放占用的图片文件  
  80.             img.Dispose();  
  81.             grp.Dispose();  
  82.             // 保存缩略图  
  83.             thm.Save(strPath);        // 如果不设置图片质量,可直接保存  
  84.             thm.Dispose();  
  85.         }  
  86.   
  87.         public static string GetNodeMap(string strData)  
  88.         {  
  89.             StringBuilder sb = new StringBuilder();  
  90.             if (String.IsNullOrEmpty(strData))  
  91.             {  
  92.                 sb.Append("subgraph cluster_app1 {label=应用系统1 app1[image=\"../../images/Topology/app.png\"];}");  
  93.                 sb.Append("subgraph cluster_vm1 {label=虚拟机1 vm1[image=\"../../images/Topology/vm.png\"];}");  
  94.                 sb.Append("subgraph cluster_vm2 {label=虚拟机2 vm2[image=\"../../images/Topology/vm.png\"];}");  
  95.                 sb.Append("subgraph cluster_svr1 {label=服务器1 svr1[image=\"../../images/Topology/svr.png\"];}");  
  96.                 sb.Append("subgraph cluster_sw1 {label=交换机1 sw1[image=\"../../images/Topology/sw.png\"];}");  
  97.                 sb.Append("subgraph cluster_tap1 {label=磁带机1 tap1[image=\"../../images/Topology/tape.png\"];}");  
  98.   
  99.                 sb.Append("app1 -> vm1 [label=安装于]");  
  100.                 sb.Append("app1 -> vm2 [label=安装于]");  
  101.                 sb.Append("vm1 -> svr1 [label=承载于]");  
  102.                 sb.Append("vm2 -> svr1 [label=承载于]");  
  103.                 sb.Append("svr1 -> sw1 [label=连接]");  
  104.                 sb.Append("svr1 -> tap1 [label=连接]");  
  105.             }  
  106.             else {  
  107.                 sb.Append(strData);  
  108.             }  
  109.             //前面一段字符  
  110.   
  111.             StringBuilder sb2 = new StringBuilder();  
  112.             sb2.Append("digraph G {\n");  
  113.             sb2.Append("compound=true;\n");  
  114.             sb2.Append("ranksep=0.5;\n");  
  115.             sb2.Append("nodesep=0.5;\n");  
  116.             sb2.Append("rankdir=LR;\n");  
  117.             sb2.Append("graph [penwidth=0, labelloc=\"b\", fontname=simsun, fontcolor=dodgerblue3, fontsize=10]\n");  
  118.             sb2.Append("node [shape=plaintext, label=\"\"]\n");  
  119.             sb2.Append("edge [color=brown, fontname=simsun, fontcolor=brown1, fontsize=10, weight=1.2];\n");  
  120.   
  121.             //string dotSource_temp = sb2.ToString() + strData; //sb.ToString();  
  122.             string dotSource_temp = sb2.ToString() + sb.ToString();  
  123.             string dotFileName_temp = Path.GetRandomFileName();  
  124.             string dirPath = GetTempDirPath();  
  125.             if (dirPath == "") {  
  126.                 return "";  
  127.             }  
  128.             string dotFileName = Path.ChangeExtension(Path.Combine(dirPath , Path.GetFileName(dotFileName_temp)), ".dot");  
  129.             string pngFile = Path.ChangeExtension(dotFileName, ".png");  
  130.             //string pngFile_temp=  
  131.             using (StreamWriter writer = new StreamWriter(dotFileName))  
  132.             {  
  133.                 writer.Write(dotSource_temp);  
  134.             }  
  135.             string dotExePath_temp = System.Configuration.ConfigurationManager.AppSettings["dotExePath"as string;  
  136.             //调用服务器端exe进程  
  137.             ProcessStartInfo info = new ProcessStartInfo()  
  138.             {  
  139.                 FileName = dotExePath_temp,  
  140.                 WorkingDirectory = Path.GetDirectoryName(dotFileName),  
  141.                 Arguments = string.Concat("-Tpng -o ", pngFile, " ", dotFileName),  
  142.                 RedirectStandardInput = false,  
  143.                 RedirectStandardOutput = false,  
  144.                 RedirectStandardError = true,  
  145.                 UseShellExecute = false,  
  146.                 CreateNoWindow = true  
  147.             };  
  148.             try  
  149.             {  
  150.                 using (Process exe = Process.Start(info))  
  151.                 {  
  152.                     exe.WaitForExit();  
  153.                     if (0 == exe.ExitCode)  
  154.                     {  
  155.                         System.Web.HttpContext.Current.Response.Write(pngFile);  
  156.                     }  
  157.                     else  
  158.                     {  
  159.                         string errMsg;  
  160.                         using (StreamReader stdErr = exe.StandardError)  
  161.                         {  
  162.                             errMsg = stdErr.ReadToEnd();  
  163.                         }  
  164.                         //System.Web.HttpContext.Current.Response.Write(errMsg);  
  165.                     }  
  166.                 }  
  167.             }  
  168.             catch(Exception ex)  
  169.             {  
  170.                 return "";  
  171.             }  
  172.             String path="~/TempFile/Graphviz/"+Path.GetFileName(pngFile);  
  173.             return path;  
  174.         }//---- end of GetNodeMap ----  
  175.   
  176.         /// <summary>  
  177.         /// 取得临时文件夹路径  
  178.         /// </summary>  
  179.         /// <returns></returns>  
  180.         private static string GetTempDirPath()  
  181.         {  
  182.             string path = System.Web.HttpContext.Current.Server.MapPath("~")+"\\TempFile\\Graphviz";  
  183.             if (!Function.CreateDir(path))  
  184.             {  
  185.                 return "";  
  186.             }  
  187.             return path;  
  188.         }  
  189.   
  190.         /// <summary>  
  191.         /// 取得图片保存路径  
  192.         /// </summary>  
  193.         /// <returns></returns>  
  194.         private static string GetImgSavePath()  
  195.         {  
  196.             string path = System.Web.HttpContext.Current.Server.MapPath("~") + "\\images\\Topology";  
  197.             if (!Function.CreateDir(path))  
  198.             {  
  199.                 return "";  
  200.             }  
  201.             return path;  
  202.         }  
  203.     }//end of class  
  204.   
  205.     public class Function  
  206.     {  
  207.         /// <summary>  
  208.         /// 根据目录创建文件夹,如果存在就不创建  
  209.         /// </summary>  
  210.         /// <param name="path"></param>  
  211.         /// <returns></returns>  
  212.         public static bool CreateDir(string path)  
  213.         {  
  214.             bool result = true;  
  215.             DirectoryInfo dir = new DirectoryInfo(path);  
  216.             //目录不存在  
  217.   
  218.             if (!dir.Exists)  
  219.             {  
  220.                 try  
  221.                 {  
  222.                     dir.Create();  
  223.   
  224.                 }  
  225.                 catch (Exception e)  
  226.                 {  
  227.                     result = false;  
  228.                 }  
  229.             }  
  230.   
  231.             return result;  
  232.         }  
  233.     }//end of class  
  234. }//end of namespace  

4. 加测试数据

  1. CREATE TABLE Graph(  
  2.     ID  CHAR(4) PRIMARY KEY,  
  3.     PID CHAR(4) NOT NULL,  
  4.     Title NVARCHAR(20) NOT NULL,  
  5.     RelationShip NVARCHAR(10) NOT NULL,  
  6.     Img VARCHAR(200) NOT NULL  
  7. )  
  8. GO  
  9. --填充数据  
  10. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('1000','','应用系统','安装于','../../images/Topology/app.png')  
  11. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('2001','1000','虚拟机1','承载于','../../images/Topology/vm.png')  
  12. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('2002','1000','虚拟机2','承载于','../../images/Topology/vm.png')  
  13. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('2003','1000','虚拟机1','承载于','../../images/Topology/vm.png')  
  14. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('3001','2001','服务器1','连接','../../images/Topology/svr.png')  
  15. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('3002','2001','服务器2','连接','../../images/Topology/svr.png')  
  16. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('3003','2002','服务器3','连接','../../images/Topology/svr.png')  
  17. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('4001','3001','交换机1','连接','../../images/Topology/sw.png')  
  18. INSERT INTO Graph(ID,PID,Title,RelationShip,Img) VALUES('4002','3002','磁带机2','连接','../../images/Topology/tape.png')  

5. 页面调用:
[csharp] view plain copy
  1. <%@ Page Language="C#" AutoEventWireup="true" CodeFile="Default.aspx.cs" Inherits="_Default" %>  
  2.   
  3. <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">  
  4.   
  5. <html xmlns="http://www.w3.org/1999/xhtml">  
  6. <head runat="server">  
  7.     <title>无标题页</title>  
  8. </head>  
  9. <body>  
  10.     <form id="form1" runat="server">  
  11.     <div>  
  12.         <asp:Image ID="Image1" runat="server" />  
  13.     </div>  
  14.     </form>  
  15. </body>  
  16. </html>  

[csharp] view plain copy
  1. using System;  
  2. using System.Collections;  
  3. using System.Configuration;  
  4. using System.Data;  
  5. using System.Linq;  
  6. using System.Web;  
  7. using System.Web.Security;  
  8. using System.Web.UI;  
  9. using System.Web.UI.HtmlControls;  
  10. using System.Web.UI.WebControls;  
  11. using System.Web.UI.WebControls.WebParts;  
  12. using System.Xml.Linq;  
  13. using Module.Common;  
  14. using System.Text;  
  15.   
  16. public partial class _Default : System.Web.UI.Page  
  17. {  
  18.     protected void Page_Load(object sender, EventArgs e)  
  19.     {  
  20.         if (!this.IsPostBack) {  
  21.             LoadInfo();  
  22.         }  
  23.     }  
  24.   
  25.     private void LoadInfo()  
  26.     {  
  27.         string sql = "SELECT * FROM Graph";  
  28.         DataTable dt = DBHelper.GetDataTableBySql(sql);  
  29.         StringBuilder sb = new StringBuilder();  
  30.         if (dt == null || dt.Rows.Count == 0)  
  31.             return;  
  32.   
  33.         BuildGraphNodes(sb,dt,"",1,5);  
  34.   
  35.         String imgUrl = GraphvizHelper.GetNodeMap(sb.ToString());  
  36.         this.Image1.ImageUrl = imgUrl;  
  37.   
  38.         GraphvizHelper.SaveWebImgToLocal("http://hiphotos.baidu.com/yuangengqiang/pic/item/f9eb16e8007ae310b90e2dc3.jpg");  
  39.     }  
  40.   
  41.     private void BuildGraphNodes(StringBuilder sb, DataTable dt, string pid, int depth, int maxDepth)   
  42.     {  
  43.         if(dt==null || dt.Rows.Count==0 || depth > maxDepth )  
  44.             return;  
  45.   
  46.         DataRow[] drArr = dt.Select( String.Format("PID='{0}'",pid) );  
  47.         if ( drArr == null || drArr.Length == 0)  
  48.             return;  
  49.   
  50.         foreach (DataRow dr in drArr) {  
  51.             sb.AppendFormat("subgraph cluster_id{0} {{label=\"{1}\" id{0}[image=\"{2}\"];}}\n",  
  52.                 dr["ID"as string, ((dr["Title"as string)??"").Replace("\"","'"), dr["Img"as string);  
  53.   
  54.             DataRow[] drSubArr = dt.Select(string.Format("PID='{0}'", dr["ID"as String));  
  55.             if (depth < maxDepth)  
  56.             {  
  57.                 foreach (DataRow drSub in drSubArr)  
  58.                 {  
  59.                     sb.AppendFormat("id{0} -> id{1} [label=\"{2}\"]\n", ((dr["ID"as string) ?? "").Replace("\"""'"), ((drSub["ID"as string) ?? "").Replace("\"""'"), dr["RelationShip"as string);  
  60.                 }  
  61.             }  
  62.             BuildGraphNodes(sb, dt, dr["ID"as String, depth + 1, maxDepth);  
  63.         }  
  64.     }  
  65. }  

猜你喜欢

转载自blog.csdn.net/u013452472/article/details/42082449