SPS Searching of InfoPath file attachments - InfoPath Dev Sign in | Join | Help in SharePoint Integration InfoPath (Entire Site) InfoPath Dev InfoPath Dev is dedicated to bringing you the information and tools you need to be successful in your Microsoft Office InfoPath development projects. Home Blogs Forums Photos Downloads InfoPath Dev » InfoPath » SharePoint Integration » SPS Searching of InfoPath file attachments SPS Searching of InfoPath file attachments Last post 05-31-2007 12:49 AM by darryl2912. 9 replies. Page 1 of 1 (10 items) Sort Posts: Oldest to newest Newest to oldest Previous Next 11-08-2005 01:50 PM rdcpro Joined on 11-08-2005 USA Posts 6 SPS Searching of InfoPath file attachments Reply Contact It doesn't seem like SharePoint can crawl/search the content of an InfoPath file attachment, at least not out of the box. This seems strange to me, since that would be a fairly common scenario for InfoPath/SharePoint integration with attachments. So, maybe I'm overlooking something. Does anyone know of a way to get SharePoint to crawl a file attachment in an InfoPath form that doesn't involve programmatically extracting the encoded binary from the form and saving it separately to a doc lib? Hopefully there is an "out of the box" solution I'm overlooking, or else a widget that we could buy for this. Otherwise I'll write the code to do it, and plug it into an existing web service...Thanks in advance,Mike 11-08-2005 02:25 PM In reply to AndersR Joined on 10-20-2005 Denmark Posts 138 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Do you mean an IP file attachment in an IP xml file?Those are stored in base64 encoding, so i see no obvious way to index them, especially because IP add a special header to them (containing filename, icon etc) that you need to remove programmaticly to access the file outside IP.//AndersR 11-08-2005 02:34 PM In reply to rdcpro Joined on 11-08-2005 USA Posts 6 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Yes, that's what I was referring to. It seems pretty limiting to have InfoPath forms with attachments that can't be indexed. I know that I can do it programmatically, and of course I'll have to read the header structure as well to get the filename, among other things. But I was hoping there was something simpler I was overlooking.Regards,Mike Sharp 11-09-2005 12:34 AM In reply to Patrick Halstead Joined on 08-08-2006 Posts 5,112 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact SPS can do this. You have to do some special stuff to make it happen but it is doable. We have a solution that uses search. However, we also chose to provide an InfoPath form that searches the form library since we had more control over it. SPS search wasn't configurable enough for our solution requirements.Attachments is a bigger issue. Don't know if this is going to be handled or not in the next version.Patrick Halstead [InfoPath MVP]InfoPathDev Patrick HalsteadProject Manager at Qdabra 11-09-2005 10:11 AM In reply to rdcpro Joined on 11-08-2005 USA Posts 6 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Oh, I'd say if you're willing to write code to work with SharePoint's query service, its quite configurable, especially if you write an IFilter for any special stuff (such as custom metadata). But yes, attachments are the issue for me. I can search the InfoPath form just fine.I guess I'll modify my FormSubmitService to extract the attachment, and PUT it to a separate SharePoint document library. Thanks!Regards,Mike Sharp 11-09-2005 02:05 PM In reply to AndersR Joined on 10-20-2005 Denmark Posts 138 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Let me know if you run into trouble extracting the attachments and adding them to SPS.I already did this, and you need to tweak both IP and SPS a bit to make it happen:-no web service makes you add images with meta data, so if meta data is an issue you need either to create a custom SPS web service or use FP-Remote Procedure Calls. If no meta data is needed, the Upload method of Imaging.asmx is your friend. Creating a custom web service for sharepoint is straight forward thoughhttp://msdn.microsoft.com/library/default.asp?url=/library/en-us/odc_SP2003_ta/html/ODC_WritingCustomWebServicesforSPPT.asp-extracting the headers takes some effort. Matthew Blain (co-writer of Mr Halstead's book "Developing solutions with MS InfoPath") created some code that does this. The pages with his InfoPath tips are down at the moment, but you can grab them using the WayBackMachine:http://web.archive.org/web/20041009132349/http://tips.serriform.com/CSharpCreateInfoPathAttachment.htmhth//AndersR 11-09-2005 04:33 PM In reply to rdcpro Joined on 11-08-2005 USA Posts 6 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Thanks Anders, Even though Matthew is creating the InfoPath header (and I want to extract it), that example will save me quite a bit of time. I figured out the header structure from the documentation, but there were a few parts that weren't completely clear (e.g., it mentioned I needed a non-ASCII character, but didn't say it should be a null!). And I hadn't noticed that the filename length was in characters, not bytes...I probably would have wasted some time before I figured that out! ;^)I can't help thinking that what would really be useful here is a new InfoPath IFilter...I've had great success with a custom HTML IFilter I use to index our content management system. In that case, I wouldn't have to mess with the attachment in the InfoPath form at all, and I could deal with any IP form posted to SharePoint, not just those that are processed with my web service. But, it's probably less work to modify my web service to strip the attachment anyway.Thanks again,Mike Sharp 11-10-2005 12:15 AM In reply to AndersR Joined on 10-20-2005 Denmark Posts 138 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact At the end if the post i have pasted my version of the code from Matthews and Patricks book (basicly i translated the VB from the book to C# using a reflector). Some conversions were made, for example i use a class not a struct because of null handling.You use it like this:InfoPathAttachment attachment = new InfoPathAttachment();try{ //remove binary InfoPath header attachment = InfoPathAttachment.DecodeAttachment(document.text);}catch (Exception e){ System.Diagnostics.Debug.WriteLine(e); throw new Exception("UploadDocument: InfoPath attachment decoding error: " + e);}byte[] bytes = attachment.FileData;string fileName = attachment.FileName.Substring(0, attachment.FileName.Length - 1);//remove terminating zeroThen its just a matter of calling your imaging or custom web service.Remember when you recieve the infopath attachment filename, that it is has a terminating zero, so you need to remove the last char to make your web service call well-formed.have fun!//AndersRP.S a shame your first name isnt Carl or something! C Sharp would be the coolest coding name ever :-Dusing System;using System.Text;using System.Runtime.InteropServices;using System.Security.Permissions;namespace Creuna.InfoPath{ public class InfoPathAttachment { // Fields public byte[] FileData; public string FileName; /// <summary> /// .NET representation of the InfoPath File Attachment Header /// </summary> [ StructLayout(LayoutKind.Sequential, Pack=1) ] private class AttachmentStructure { public int Signature; public int HeaderSize; public int InfopathVersion; public int Reserved; public int Filesize; public int FilenameCharLen; } /// <summary> /// converts a byte array to an AttachmentStructure /// </summary> /// <param name="attachmentArray"></param> /// <returns>AttachmentStructure</returns> private static AttachmentStructure BytesToHeaderStructure( byte[] attachmentArray ) { int structureLength = Marshal.SizeOf(typeof(InfoPathAttachment.AttachmentStructure)); if (attachmentArray.Length < structureLength) return null; //Allocates memory from the unmanaged memory IntPtr pointer = Marshal.AllocHGlobal(structureLength); //Copy data from a one-dimensional, managed 8-bit unsigned integer array to an unmanaged memory pointer Marshal.Copy(attachmentArray, 0, pointer, structureLength); //Marshal data from an unmanaged block of memory to a managed object AttachmentStructure attachmentStructure = (AttachmentStructure) Marshal.PtrToStructure(pointer, typeof(AttachmentStructure)); Marshal.FreeHGlobal(pointer); return attachmentStructure; } public static int Base64EncodedLength(int cb) { //The base64 encoded header will always be 4/3 the size of the //binary version, rounded up to a multiple of 4. return (int) Math.Round((double) (Math.Ceiling(((double) cb) / 3) * 4)); } /// <summary> /// /// </summary> /// <param name="InnerTextAttachment"></param> /// <returns></returns> public static InfoPathAttachment DecodeAttachment(string InnerTextAttachment) { AttachmentStructure attachmentStructure = new AttachmentStructure(); InfoPathAttachment infoPathAttachment = new InfoPathAttachment(); //get encoded length of header int cbHeaderEncoded = InfoPathAttachment.Base64EncodedLength(Marshal.SizeOf(attachmentStructure.GetType())); if ( InnerTextAttachment.Length < cbHeaderEncoded ) { throw new Exception("Encoded string is not long enough to include header."); } //decode header from string to byte byte[] rgHeader = Convert.FromBase64String(InnerTextAttachment.Substring(0, cbHeaderEncoded)); //decode header from bytes to structure attachmentStructure = InfoPathAttachment.BytesToHeaderStructure(rgHeader); //check the signature //1095125447 dec is 0x414649c7 hex, or {199, 73, 70, 65}. if (!attachmentStructure.Signature.Equals(0x414649c7)) { throw new Exception("Signature does not match InfoPath attachment signature."); } //Check the header size. //The size of the header does not include the size of the signature. int headerSizeRequired = Marshal.SizeOf(attachmentStructure.GetType()) - 4; if (!attachmentStructure.HeaderSize.Equals(headerSizeRequired)) { throw new Exception("Header size does not match expected size."); } //Check body int cbBodyEncoded = InfoPathAttachment.Base64EncodedLength((attachmentStructure.FilenameCharLen * 2) + attachmentStructure.Filesize); if (InnerTextAttachment.Length < (cbHeaderEncoded + cbBodyEncoded)) { throw new Exception("Encoded string is not long enough to include body."); } byte[] rgBody = Convert.FromBase64String(InnerTextAttachment.Substring(cbHeaderEncoded, cbBodyEncoded)); //copy out filename infoPathAttachment.FileName = Encoding.Unicode.GetString(rgBody, 0, attachmentStructure.FilenameCharLen * 2); //copy out the rest of the file bytes infoPathAttachment.FileData = (byte[]) Array.CreateInstance(typeof(byte), attachmentStructure.Filesize); Array.Copy(rgBody, (int) (attachmentStructure.FilenameCharLen * 2), infoPathAttachment.FileData, 0, attachmentStructure.Filesize); return infoPathAttachment; } } } 05-31-2007 12:36 AM In reply to darryl2912 Joined on 05-30-2007 Posts 4 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Hi AndersonRHow do you use this code?I am in Sharepoint 2007 and I want to extract the InfoPath File Attachment out of a form Library and then place that attachment that I extracted into a Custom List. How would you do this using your code? A web part or a feature. I am not sure? Please help.Kind Regardsdarryl2912 05-31-2007 12:49 AM In reply to darryl2912 Joined on 05-30-2007 Posts 4 Re: SPS Searching of InfoPath file attachments Mark as Not AnswerMark as Answer... Reply Contact Hi rdcpro, Can you help me by using your FormSubmitService to be able to submit the file attachment attached to a IP form and place it into a SharePoint 2007 List? Please HelpKind Regardsdarryl2912 Page 1 of 1 (10 items) Copyright © 2003-2019 Qdabra Software. All rights reserved.View our Terms of Use.
Hi AndersonR
How do you use this code?
I am in Sharepoint 2007 and I want to extract the InfoPath File Attachment out of a form Library and then place that attachment that I extracted into a Custom List. How would you do this using your code? A web part or a feature. I am not sure?
Please help.
Kind Regards
darryl2912
Hi rdcpro,
Can you help me by using your FormSubmitService to be able to submit the file attachment attached to a IP form and place it into a SharePoint 2007 List?
Please Help