Sub Application_Start(ByVal sender As Object, ByVal e As EventArgs)
Dim appSettings As NameValueCollection = _
System.Configuration.ConfigurationManager.AppSettings
Application("Url") = appSettings("Url")
Application("SslConvPath") = appSettings("SslConvPath")
End Sub
public override void Write(byte[] buffer, int offset, int count)
{
int nCharCnt = m_dec.GetCharCount(buffer, offset, count);
char[] result = new char[nCharCnt];
int nDecoded = m_dec.GetChars(buffer, offset, count, result, 0);
char[] temp = new char[nCharCnt*2];
if (nDecoded <= 0)
return;
int cPos = 0;
for (int nPos=0; nPos<=nDecoded; ++nPos) {
bool bLastLine = nPos == nDecoded;
char c;
if (nPos < nDecoded) {
c = result[nPos];
} else {
c = '\n';
}
temp[cPos++] = c;
if (c == '\n') {
int len;
if (this.m_Url.Length > 0) {
string str;
str = new string(temp, 0, cPos);
foreach (string path in this.m_convPaths) {
string s= "href=\"" + path;
if (str.IndexOf(s) >= 0) {
// リンク先を置換する
str = str.Replace(path, "#DUMMY#");
str = str.Replace("#DUMMY#", m_Url + path);
}
}
if (bLastLine) {
str = str.Substring(0, str.Length - 1);
}
str.ToCharArray().CopyTo(temp, 0);
len = str.Length;
} else {
len = cPos-1;
}
m_streamWriter.Write(temp, 0, len);
cPos = 0;
}
}
m_streamWriter.Flush();
} // end of Write()
#region Streamクラスで実装の必要なそのほかその他のメソッド/プロパティ
public override int Read(byte[] buffer, int offset, int count) {
throw new NotSupportedException(); }
public override bool CanRead {
get { return false; } }
public override bool CanSeek {
get { return false; } }
public override bool CanWrite {
get { return true; } }
public override long Length {
get { throw new NotSupportedException(); } }
public override long Position {
get { throw new NotSupportedException(); }
set { throw new NotSupportedException(); }
}
public override void Flush() {
m_stream.Flush();
}
public override long Seek(long offset, SeekOrigin origin) {
throw new NotSupportedException();
}
public override void SetLength(long value) {
throw new NotSupportedException();
}
#endregion
} // end of class
} // end of namespace
Imports System
Imports System.IO
Imports System.Diagnostics
Imports System.Text
Namespace MyWebSite
Public Class SslFilter
Inherits Stream
Private m_stream As Stream
Private m_streamWriter As StreamWriter
Private m_dec As Decoder
Private m_Url As String
Private m_enc As Encoding
Private m_convPaths As String()
' コンストラクタ
Public Sub New(ByVal stm As Stream, ByVal URL As String, ByVal sConvPath As String)
m_enc = Encoding.GetEncoding("shift_jis")
m_stream = stm
m_Url = URL
m_streamWriter = New StreamWriter(m_stream, m_enc)
m_dec = m_enc.GetDecoder()
m_convPaths = sConvPath.Split(","C)
End Sub
Public Overloads Overrides Sub Write(ByVal buffer As Byte(), ByVal offset As Integer, ByVal count As Integer)
Dim nCharCnt As Integer = m_dec.GetCharCount(buffer, offset, count)
Dim result As Char() = New Char(nCharCnt - 1) {}
Dim nDecoded As Integer = m_dec.GetChars(buffer, offset, count, result, 0)
Dim temp As Char() = New Char(nCharCnt * 2 - 1) {}
If nDecoded <= 0 Then
Return
End If
Dim cPos As Integer = 0
For nPos As Integer = 0 To nDecoded
Dim bLastLine As Boolean = (nPos = nDecoded)
Dim c As Char
If nPos < nDecoded Then
c = result(nPos)
Else
c = Chr(10)
End If
temp(System.Math.Max(System.Threading.Interlocked.Increment(cPos),cPos - 1)) = c
If c = Chr(10) Then
Dim len As Integer
If Me.m_Url.Length > 0 Then
Dim str As String
str = New String(temp, 0, cPos)
For Each path As String In Me.m_convPaths
Dim s As String = "href=""" + path
If str.IndexOf(s) >= 0 Then
' リンク先を置換する
str = str.Replace(path, "#DUMMY#")
str = str.Replace("#DUMMY#", m_Url + path)
End If
Next
If bLastLine Then
str = str.Substring(0, str.Length - 1)
End If
str.ToCharArray().CopyTo(temp, 0)
len = str.Length
Else
len = cPos - 1
End If
m_streamWriter.Write(temp, 0, len)
cPos = 0
Else
End If
Next
m_streamWriter.Flush()
End Sub ' end of Write()
#Region "Streamクラスで実装の必要なそのほかのメソッド/プロパティ"
Public Overloads Overrides Function Read(ByVal buffer As Byte(), ByVal offset As Integer, ByVal count As Integer) As Integer
Throw New NotSupportedException()
End Function
Public Overloads Overrides ReadOnly Property CanRead() As Boolean
Get
Return False
End Get
End Property
Public Overloads Overrides ReadOnly Property CanSeek() As Boolean
Get
Return False
End Get
End Property
Public Overloads Overrides ReadOnly Property CanWrite() As Boolean
Get
Return True
End Get
End Property
Public Overloads Overrides ReadOnly Property Length() As Long
Get
Throw New NotSupportedException()
End Get
End Property
Public Overloads Overrides Property Position() As Long
Get
Throw New NotSupportedException()
End Get
Set
Throw New NotSupportedException()
End Set
End Property
Public Overloads Overrides Sub Flush()
m_stream.Flush()
End Sub
Public Overloads Overrides Function Seek(ByVal offset As Long, ByVal origin As SeekOrigin) As Long
Throw New NotSupportedException()
End Function
Public Overloads Overrides Sub SetLength(ByVal value As Long)
Throw New NotSupportedException()
End Sub
#End Region
End Class ' end of class
End Namespace ' end of namespace
これでWebページの出力時にSslFilterクラスのWriteメソッドが呼び出されるようになり、リンクの変換が行われる。SSI(Server Side Include)を記述している場合は、SSIが展開された状態でWriteメソッドが呼び出されるので、SSIで指定したファイルに記述されたリンクも正しく変換される。
namespace MyWebSite
{
public partial class app : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
// フィルタのインスタンス化
SslFilter fltr = new SslFilter(
Response.Filter,
(string)Application["SSLURL"],
(string)Application["SslConvPath"]);
// 独自のフィルタをセットする
Response.Filter = fltr;
}
}
}
Namespace MyWebSite
Public Partial Class app
Inherits System.Web.UI.Page
Protected Sub Page_Load(ByVal sender As Object, ByVal e As EventArgs) Handles Me.Load
' フィルタのインスタンス化
Dim fltr As New SslFilter( _
Response.Filter, _
DirectCast(Application("SSLURL"), String), _
DirectCast(Application("SslConvPath"), String))
' 独自のフィルタをセットする
Response.Filter = fltr
End Sub
End Class
End Namespace