using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Xml;
using Lucene.Net.Store;
using Lucene.Net.Index;
using Lucene.Net.Documents;
using ICSharpCode.SharpZipLib.Zip;
using System.IO;
namespace iReaper.Source{
public class IndexBuilder
{
static string _indexPath = "";
public static void Init()
{
// Get server
string relativePath = System.Web.Configuration.WebConfigurationManager.AppSettings["IndexData"];
_indexPath = HttpContext.Current.Server.MapPath(relativePath) ;
// Register event handler
OriginalContentManager.Current.OnXmlSynchorized += new EventHandler(OnXmlSync_CreateIndex);
}
private static void OnXmlSync_CreateIndex(object sender, EventArgs e)
{
string infoXmlPath = OriginalContentManager.Current.InfoXmlPath;
XmlDocument xmldoc = new XmlDocument();
xmldoc.Load(infoXmlPath);
RAMDirectory dir = new RAMDirectory();
IndexWriter writer = new IndexWriter(dir, new Lucene.Net.Analysis.CJK.CJKAnalyzer(), true, IndexWriter.MaxFieldLength.UNLIMITED);
foreach (XmlNode node in xmldoc.SelectNodes("//R"))
{
Document doc = new Document();
// ID
var newsId = node.SelectSingleNode("newsID");
doc.Add(new Field("id", newsId.InnerText, Field.Store.YES, Field.Index.NOT_ANALYZED_NO_NORMS));
// Headline
var headline = node.SelectSingleNode("headline");
doc.Add(new Field("", headline.InnerText, Field.Store.NO, Field.Index.ANALYZED));
// Desc
var desc = node.SelectSingleNode("description");
doc.Add(new Field("", desc.InnerText, Field.Store.NO, Field.Index.ANALYZED));
foreach (XmlNode aNode in node.SelectNodes("a"))
{
string key = aNode.Attributes["attCatID"].Value;
string value = aNode.Attributes["attValue"].Value;
if (string.IsNullOrEmpty(value))
{
continue;
}
switch (key)
{
case "speaker":
doc.Add(new Field("speaker", value, Field.Store.NO, Field.Index.NOT_ANALYZED));
break;
case "products":
doc.Add(new Field("", value, Field.Store.NO, Field.Index.ANALYZED));
break;
case "date":
doc.Add(new Field("time",
DateTools.DateToString(DateTime.Parse(value), DateTools.Resolution.DAY),
Field.Store.NO,
Field.Index.NOT_ANALYZED_NO_NORMS));
break;
case "tech":
doc.Add(new Field("", value, Field.Store.NO, Field.Index.ANALYZED));
break;
case "series":
doc.Add(new Field("", value, Field.Store.NO, Field.Index.ANALYZED));
break;
case "rating":
doc.Add(new Field("rate", value, Field.Store.NO, Field.Index.NOT_ANALYZED_NO_NORMS));
break;
case "level":
doc.Add(new Field("level", value, Field.Store.NO, Field.Index.NOT_ANALYZED_NO_NORMS));
break;
}
}
writer.AddDocument(doc);
}
writer.Optimize();
writer.Close();
// Zip to wwwroot
PackageIndexFile(dir);
}
private static void PackageIndexFile(RAMDirectory dir)
{
FileStream indexZipFS = new FileStream(_indexPath,
FileMode.Create,
FileAccess.Write,
FileShare.None,
1024,
FileOptions.None);
ZipOutputStream zipOut = new ZipOutputStream(indexZipFS);
zipOut.IsStreamOwner = true;
int index = 0;
byte[] buffer = new byte[4096];
foreach (string name in dir.ListAll())
{
ZipEntry entry = new ZipEntry(name);
entry.CompressionMethod = CompressionMethod.Deflated;
zipOut.PutNextEntry(entry);
IndexInput input = dir.OpenInput(name);
long length = input.Length();
long iRead = 0;
while (iRead < length)
{
int len = (int)(length - iRead) > 4096 ? 4096 : (int)(length - iRead);
input.ReadBytes(buffer, 0, len);
zipOut.Write(buffer, 0, len);
iRead += len;
}
index++;
}
// Add info.xml
string infoPath = OriginalContentManager.Current.InfoXmlPath;
using(FileStream fs = new FileStream(infoPath, FileMode.Open))
{
long length = fs.Length;
long lenRead = 0;
ZipEntry entry = new ZipEntry("info.xml");
entry.CompressionMethod = CompressionMethod.Deflated;
zipOut.PutNextEntry(entry);
while (lenRead < length)
{
int len = (int)(length - lenRead) > 4096 ? 4096 : (int)(length - lenRead);
int iRead = fs.Read(buffer, 0, len);
zipOut.Write(buffer, 0, iRead);
lenRead += iRead;
}
fs.Close();
}
zipOut.Finish();
zipOut.Close();
}
}
}
|