Infopath File attachment kontrolündeki dosyayı programsal olarak kaydetmek ve bu dosyayı mail ile göndermek
Formumuz’a bir adet File attachment kontrolu,bir adet Text Box kontrolü ve buton kontrolü ekliyoruz.
Buton kontrolüne tıklandığında
textbox’a eklenen dosyanın adı tutulacak. İleriki aşamalarda Sharepoint
Designer kullanılarak textbox’ta tutulan bu dosya adı ile ilgili dosyayı
çağırıp göstereceğiz.
Buton Kontrolüne tıklandığında
eklenen dosya binary olarak şifrelenir (encode)
Bunun için infopath
formumuzda InfoPathAttachmentEncoder.cs
adında yeni bir class oluştururuz.
InfoPathAttachmentEncoder.cs
using System;
using System.Text;
using System.IO;
using System.Security.Cryptography;
/// <summary>
/// InfoPathAttachment dosya
verisini infopath’in dosya ekleme formatına çevirir.
/// </summary>
public class
InfoPathAttachmentEncoder
{
private string base64EncodedFile = string.Empty;
private string fileName;
private byte[] fileData;
/// <summary>
/// Creates an encoder to create an InfoPath attachment
string.
/// </summary>
/// <param
name="fileName"></param>
/// <param
name="fileData"></param>
public
InfoPathAttachmentEncoder(string fileName, byte[] fileData)
{
if
(fileName == string.Empty)
throw
new ArgumentException("Must specify file name", "fileName");
if
(fileData.Length == 0)
throw
new ArgumentNullException("fileData","File
is empty");
this.fileName
= fileName;
this.fileData
= fileData;
}
/// <summary>
/// Returns a Base64 encoded string.
/// </summary>
/// <returns>String</returns>
public string ToBase64String()
{
if
(base64EncodedFile != string.Empty)
return
base64EncodedFile;
// This
memory stream will hold the InfoPath file attachment buffer before Base64
encoding.
MemoryStream
ms = new MemoryStream();
// This memory
stream will hold the current file to be changed.
MemoryStream
msOld = new MemoryStream(fileData);
// Get the
file information.
using (BinaryReader br = new
BinaryReader(msOld))
{
string
fileName = this.fileName;
uint
fileNameLength = (uint)fileName.Length + 1;
byte[]
fileNameBytes = Encoding.Unicode.GetBytes(fileName);
using
(BinaryWriter bw = new
BinaryWriter(ms))
{
//
Write the InfoPath attachment signature.
bw.Write(new byte[] { 0xC7,
0x49, 0x46, 0x41 });
//
Write the default header information.
bw.Write((uint)0x14); // size
bw.Write((uint)0x01); // version
bw.Write((uint)0x00); // reserved
//
Write the file size.
bw.Write((uint)br.BaseStream.Length);
//
Write the size of the file name.
bw.Write((uint)fileNameLength);
//
Write the file name (Unicode encoded).
bw.Write(fileNameBytes);
//
Write the file name terminator. This is two nulls in Unicode.
bw.Write(new byte[] { 0, 0 });
//
Iterate through the file reading data and writing it to the outbuffer.
byte[]
data = new byte[64
* 1024];
int
bytesRead = 1;
while
(bytesRead > 0)
{
bytesRead = br.Read(data,
0, data.Length);
bw.Write(data, 0, bytesRead);
}
}
}
// This
memorystream will hold the Base64 encoded InfoPath attachment.
MemoryStream
msOut = new MemoryStream();
using (BinaryReader br = new
BinaryReader(new
MemoryStream(ms.ToArray())))
{
// Create
a Base64 transform to do the encoding.
ToBase64Transform
tf = new ToBase64Transform();
byte[]
data = new byte[tf.InputBlockSize];
byte[]
outData = new byte[tf.OutputBlockSize];
int
bytesRead = 1;
while
(bytesRead > 0)
{
bytesRead = br.Read(data, 0,
data.Length);
if
(bytesRead == data.Length)
tf.TransformBlock(data, 0,
bytesRead, outData, 0);
else
outData =
tf.TransformFinalBlock(data, 0, bytesRead);
msOut.Write(outData, 0,
outData.Length);
}
}
msOld.Close();
msOut.Close();
return base64EncodedFile = Encoding.ASCII.GetString(msOut.ToArray());
}
}
Yazılan dosyayı okuyabilmek için infopath formumuza
InfoPathAttachmentDecoder.cs adında yeni bir class ekliyoruz.
InfoPathAttachmentDecoder.cs
using System;
using System.IO;
using System.Text;
namespace denemeimg
{
/// <summary>
/// Decodes a file attachment and saves it to a specified
path.
/// </summary>
public class InfoPathAttachmentDecoder
{
private
const int
SP1Header_Size = 20;
private
const int
FIXED_HEADER = 16;
private
int fileSize;
private
int attachmentNameLength;
private
string attachmentName;
private
byte[] decodedAttachment;
/// <summary>
/// Accepts the Base64 encoded string
/// that is the attachment.
/// </summary>
public
InfoPathAttachmentDecoder(string
theBase64EncodedString)
{
byte
[] theData = Convert.FromBase64String(theBase64EncodedString);
using(MemoryStream ms = new
MemoryStream(theData))
{
BinaryReader
theReader = new BinaryReader(ms);
DecodeAttachment(theReader);
}
}
private
void DecodeAttachment(BinaryReader
theReader)
{
//Position
the reader to get the file size.
byte[]
headerData = new byte[FIXED_HEADER];
headerData =
theReader.ReadBytes(headerData.Length);
fileSize = (int)theReader.ReadUInt32();
attachmentNameLength = (int)theReader.ReadUInt32() * 2;
byte[]
fileNameBytes = theReader.ReadBytes(attachmentNameLength);
//InfoPath
uses UTF8 encoding.
Encoding
enc = Encoding.Unicode;
attachmentName = enc.GetString(fileNameBytes,
0, attachmentNameLength - 2);
decodedAttachment =
theReader.ReadBytes(fileSize);
}
public
void SaveAttachment(string
saveLocation)
{
string
fullFileName = saveLocation;
if(!fullFileName.EndsWith(Path.DirectorySeparatorChar.ToString()))
{
fullFileName += Path.DirectorySeparatorChar;
}
fullFileName +=
attachmentName;
if(File.Exists(fullFileName))
File.Delete(fullFileName);
FileStream
fs = new FileStream(fullFileName,
FileMode.CreateNew);
BinaryWriter
bw = new BinaryWriter(fs);
bw.Write(decodedAttachment);
bw.Close();
fs.Close();
}
public
string Filename
{
get{
return attachmentName; }
}
public
byte[] DecodedAttachment
{
get{
return decodedAttachment; }
}
}
}
Buton kontrolüne tıklandığı anda bu iki class eklenen
dosyanın binary olarak yazılması ve okunması için çağrılır.
Şimdi buton
kontrolümüzün altında çalışacak kodlarımızı yazalım.
public void CTRL3_5_Clicked(object
sender, ClickedEventArgs e)
{
XPathNavigator
root = MainDataSource.CreateNavigator();
//
Eklenen Dosyayı alma
XPathNavigator
attachmentNode = root.SelectSingleNode("//my:eklenendosya",
NamespaceManager);
string
base64Attachment = attachmentNode.Value;
//InfoPathAttachmentDecoder
class' kullanarak eklenen dosyayı binary Data olarak okuyoruz.
InfoPathAttachmentDecoder
decoder =new InfoPathAttachmentDecoder(base64Attachment);
byte[]
fileData = decoder.DecodedAttachment;
root.SelectSingleNode("//my:dosyaadi", NamespaceManager).SetValue(decoder.Filename);
string
newFileName = root.SelectSingleNode("//my:dosyaadi",
NamespaceManager).Value;
//InfoPathAttachmentEncoder
class'ı kullanarak eklenen dosyanın adını tutacagımız textbox kontrolunde dosyaadını
şifreliyoruz
InfoPathAttachmentEncoder
encoder = new InfoPathAttachmentEncoder(newFileName,
fileData);
// File
Attachment control'ünde eklenen dosyayı tutma
attachmentNode.SetValue(encoder.ToBase64String());
//Eklenen
dosyanın Kayıt edileceği yer
decoder.SaveAttachment(@"\\portalnew\KullaniciBilgileriIKResimler");
}
Infopath Formumuzu çalıştırdığımızda
Attachment File controlüne tıkladığımızda ekleyecegimiz
dosyayı seçeceğimiz Attach File dialog penceresi açılır ve ilgili dosyayı
seçeriz.
Buton kontrolünün altında çalışan
decoder.SaveAttachment(@"\\portalnew\KullaniciBilgileriIKResimler");
kodu ile eklediğimiz dosyayı kaydedeceğimiz yeri gösteririz.Çünkü birazdan Sharepoint designer ile iş akışı düzenleyeceğiz.
Her yeni infopath formunda eklenen bu dosyayı kullanıcılara göstereceğiz.
SharePoint Designer ile Düzenleyeceğimiz iş akışı :
Formda FormGiris adında yeni bir field yaratıp değerini 1 olarak set edeceğiz.
FormGiris=1 Sharepoint designer da ilgili iş akışı başlayarak ilgili
kullanıcıya eklenen dosya gönderilir.
Buton kontrolünün altına aşağıdaki kodu yazıyoruz.
MainDataSource.CreateNavigator().SelectSingleNode("/my:myFields/my:FormGiris",
NamespaceManager).SetValue("1");
//Açık olan
pencereyi kapatıyoruz
Application.ActiveWindow.Close();
Yeni bir form açtık ve Form’a dosya ekledik.Gönder butonu
ile formu sharepointte ilgili form kitaplığına gönderdik.
Şimdi Sharepoint Designer kullanarak iş akışımızı
tasarlıyoruz.
Infopath formumuzu yayınladıgımız form kitaplığında yeni bir form açalım ve iş akışımızın nasıl çalıştığına bakalım.
butonuna basıldığında dosyanın adı textbox kontrolüne cicek.jpg
olarak yazılır ve FormGiris alanının değeri 1 olarak set edilir. Form
sharepoint sitesinde yayınlandığı yere kaydedilir.Ve iş akışı ilgili
kullanıcıya bu dosyayı mail yoluyla gönderir.
Form tasarlanırken Toolsà DataconnectionàGonder adında bir data bağlantısı oluşturduk.Burada formun doldurulduktan sonra saklanacağı yeri gösterdik.
FormGiris=1 ise kullanıcıya iş akışından dönen mail
Hazırlayan:Güler
ONUK
No comments:
Post a Comment