/// <summary> /// Looks up for a transform object in the cache and returns its metadata if the specified transform was found. /// </summary> /// <param name="transformName">The unique name of the transform object that is being used as a cache key.</param> /// <returns>An instance of the object carrying the XSLT transformation metadata, XSLT transformation engine and its arguments, or null if the specified transform was not found.</returns> public XslTransformSet Get(string transformName) { Guard.ArgumentNotNullOrEmptyString(transformName, "transformName"); var callToken = TraceManager.WorkerRoleComponent.TraceIn(transformName); try { XslTransformCacheItemInfo cacheItemInfo = null; XslTransformSet transformSet = null; // If extension has not been attached, the cache is not available, hence we should not be using it. if (this.transformCache != null) { if (this.transformCache.TryGetValue(transformName, out cacheItemInfo) && !cacheItemInfo.IsExpired) { transformSet = cacheItemInfo.TransformSet; } } return(transformSet); } finally { TraceManager.WorkerRoleComponent.TraceOut(callToken); } }
/// <summary> /// Puts the specified transform object and its metadata into the underlying cache. /// </summary> /// <param name="transformName">The unique name of the transform object that will be used as a cache key.</param> /// <param name="transformSet">The object carrying the XSLT transformation metadata, XSLT transformation object and its arguments.</param> public void Put(string transformName, XslTransformSet transformSet) { Guard.ArgumentNotNullOrEmptyString(transformName, "transformName"); Guard.ArgumentNotNull(transformSet, "transformSet"); var callToken = TraceManager.WorkerRoleComponent.TraceIn(transformName); try { // If extension has not been attached, the cache is not available, hence we should not be using it. if (this.transformCache != null) { XslTransformCacheItemInfo cacheItemInfo = new XslTransformCacheItemInfo(transformSet, CacheTimeToLive); this.transformCache.AddOrUpdate(transformName, cacheItemInfo, (key, oldValue) => { return(cacheItemInfo); }); } } finally { TraceManager.WorkerRoleComponent.TraceOut(callToken); } }
/// <summary> /// Instantiate a new instance of the <see cref="XslTransformCacheItemInfo"/> object using the specified XSLT transformation metadata /// and a custom cache TTL value. /// </summary> /// <param name="transformSet">The object carrying the XSLT transformation metadata, XSLT transformation object and its arguments.</param> /// <param name="timeToLive">The time value indicating how long cached items will be kept inside the cache.</param> public XslTransformCacheItemInfo(XslTransformSet transformSet, TimeSpan timeToLive) : this(transformSet) { if (timeToLive != TimeSpan.Zero) { ExpiresOn = CreatedOn.Add(timeToLive); } }
/// <summary> /// Looks up for a transform object in the cache and returns its metadata if the specified transform was found. /// </summary> /// <param name="transformName">The unique name of the transform object that is being used as a cache key.</param> /// <returns>An instance of the object carrying the XSLT transformation metadata, XSLT transformation engine and its arguments, or null if the specified transform was not found.</returns> public XslTransformSet Get(string transformName) { Guard.ArgumentNotNullOrEmptyString(transformName, "transformName"); var callToken = TraceManager.WorkerRoleComponent.TraceIn(transformName); try { XslTransformSet transformSet = null; using (ICloudBlobStorage blobStorage = this.cloudStorageProvider.GetBlobStorage(this.storageAccount.AccountName)) { XslTransformCacheItemInfo cacheItemInfo = blobStorage.Get <XslTransformCacheItemInfo>(ContainerName, transformName); if (cacheItemInfo != null && !cacheItemInfo.IsExpired) { transformSet = cacheItemInfo.TransformSet; } } return(transformSet); } catch (Exception ex) { TraceManager.WorkerRoleComponent.TraceError(ex); return(null); } finally { TraceManager.WorkerRoleComponent.TraceOut(callToken); } }
/// <summary> /// Instantiate a new instance of the <see cref="XslTransformCacheItemInfo"/> object using the specified XSLT transformation metadata. /// </summary> /// <param name="transformSet">The object carrying the XSLT transformation metadata, XSLT transformation object and its arguments.</param> public XslTransformCacheItemInfo(XslTransformSet transformSet) { Guard.ArgumentNotNull(transformSet, "transformSet"); TransformSet = transformSet; CreatedOn = DateTime.UtcNow; ExpiresOn = CreatedOn.AddSeconds(DefaultTimeToLiveSeconds); }
/// <summary> /// Applies the specified transformation map name against the source document described by the given transformation state object. /// </summary> /// <param name="transformName">Either partial or fully qualified name of the transformation map.</param> /// <param name="state">An instance of the state object carrying the information related to the source document that will be transformed.</param> /// <returns>An instance of the object used by the Scalable Transformation Service to track state transitions when performing transformations.</returns> public XslTransformState ApplyTransform(string transformName, XslTransformState state) { try { Guard.ArgumentNotNullOrEmptyString(transformName, "transformName"); Guard.ArgumentNotNull(state, "state"); Guard.ArgumentNotNullOrEmptyString(state.StorageAccount, "state.StorageAccount"); Guard.ArgumentNotNullOrEmptyString(state.ContainerName, "state.ContainerName"); Guard.ArgumentNotNullOrEmptyString(state.InputDocumentRef, "state.InputDocumentRef"); XslTransformSet transformSet = this.transformProvider.GetXslTransform(transformName); if (transformSet != null) { using (ICloudBlobStorage blobStorage = this.cloudStorageProvider.GetBlobStorage(state.StorageAccount)) using (Stream blobData = blobStorage.Get <Stream>(state.ContainerName, state.InputDocumentRef)) { if (blobData != null) { using (MemoryStream outputDoc = new MemoryStream()) using (XmlReader inputDocReader = XmlReader.Create(blobData)) { transformSet.Transform.Transform(inputDocReader, transformSet.Arguments, outputDoc); outputDoc.Seek(0, SeekOrigin.Begin); XslTransformState newState = PersistInputDocument(outputDoc); return(new XslTransformState(newState, state)); } } else { throw new InvalidOperationException(String.Format(CultureInfo.InvariantCulture, ExceptionMessages.ApplyTransformOperationFailureInputDocNotFound, state.StorageAccount, state.ContainerName, state.InputDocumentRef)); } } } else { throw new InvalidOperationException(String.Format(CultureInfo.InvariantCulture, ExceptionMessages.ApplyTransformOperationFailureTransformNotFound, transformName)); } } catch (Exception ex) { throw new CloudApplicationException(String.Format(CultureInfo.InvariantCulture, ExceptionMessages.ApplyTransformOperationFailed, ex.Message), ex); } }
/// <summary> /// Puts the specified transform object and its metadata into the underlying cache. /// </summary> /// <param name="transformName">The unique name of the transform object that will be used as a cache key.</param> /// <param name="transformSet">The object carrying the XSLT transformation metadata, XSLT transformation object and its arguments.</param> public void Put(string transformName, XslTransformSet transformSet) { Guard.ArgumentNotNullOrEmptyString(transformName, "transformName"); Guard.ArgumentNotNull(transformSet, "transformSet"); var callToken = TraceManager.WorkerRoleComponent.TraceIn(transformName); try { using (ICloudBlobStorage blobStorage = this.cloudStorageProvider.GetBlobStorage(this.storageAccount.AccountName)) { XslTransformCacheItemInfo cacheItemInfo = new XslTransformCacheItemInfo(transformSet, CacheTimeToLive); blobStorage.CreateContainer(ContainerName); blobStorage.Put <XslTransformCacheItemInfo>(ContainerName, transformName, cacheItemInfo); } } finally { TraceManager.WorkerRoleComponent.TraceOut(callToken); } }
/// <summary> /// Returns an object carrying the XSLT transformation metadata, XSLT transformation engine and its arguments. /// </summary> /// <param name="transformName">Either partial or fully qualified name of the transformation object.</param> /// <returns>An instance of the object carrying the XSLT transformation metadata, XSLT transformation engine and its arguments, or null if the specified transform was not found.</returns> public XslTransformSet GetXslTransform(string transformName) { var callToken = TraceManager.WorkerRoleComponent.TraceIn(transformName); try { ICollection <IXslTransformCacheExtension> transformCacheCollection = this.owner.Extensions.FindAll <IXslTransformCacheExtension>(); XslTransformSet transformSet = null; // If cache is enabled, try to get from the cache first. if (transformCacheCollection != null) { // Find a cached transform instance in all registered cache extensions, break at the first match. foreach (var transformCache in transformCacheCollection) { if ((transformSet = transformCache.Get(transformName)) != null) { break; } } } // Reason 1: cache miss or no caching functionality is provided via extensions. // Reason 2: transform set doesn't have the XSLT transform engine instance. // Reason 3: XSLT transform engine in the transform set doesn't have a loaded template. if (null == transformSet || null == transformSet.Transform || null == transformSet.Transform.OutputSettings) { // Try to re-use the transform metadata (if available), otherwise XslTransformMetadata metadata = transformSet != null && transformSet.Metadata != null ? transformSet.Metadata : this.metadataProvider.GetXslTransformMetadata(transformName); if (metadata != null) { XslCompiledTransform transform = new XslCompiledTransform(); XsltArgumentList arguments = new XsltArgumentList(); XsltSettings xsltSettings = new XsltSettings() { EnableDocumentFunction = true, EnableScript = true }; XmlReaderSettings readerSettings = new XmlReaderSettings() { CheckCharacters = false, IgnoreComments = true, IgnoreProcessingInstructions = true, IgnoreWhitespace = true, ValidationType = ValidationType.None }; // Read the XSLT template from the metadata and load it into XSLT transformation engine. using (StringReader rawDataReader = new StringReader(metadata.XsltContentRaw)) using (XmlReader xsltReader = XmlReader.Create(rawDataReader, readerSettings)) { transform.Load(xsltReader, xsltSettings, null); } // Check if XSLT arguments are provided. if (!String.IsNullOrEmpty(metadata.XsltArgumentsRaw)) { // Read the XSLT argument list from the metadata and load it into a XsltArgumentList collection. using (StringReader argDataReader = new StringReader(metadata.XsltArgumentsRaw)) using (XmlReader argContentReader = XmlReader.Create(argDataReader, readerSettings)) { XDocument xsltArgs = XDocument.Load(argContentReader); var extObjects = (from x in xsltArgs.Root.Descendants() select new { Namespace = x.Attribute(Resources.ExtensionObjectNamespaceAttributeName).Value, AssemblyName = x.Attribute(Resources.ExtensionObjectAssemblyAttributeName).Value, ClassName = x.Attribute(Resources.ExtensionObjectClassAttributeName).Value }); foreach (var extObjectInfo in extObjects) { Type extObjectType = Type.GetType(String.Concat(extObjectInfo.ClassName, ", ", extObjectInfo.AssemblyName), false); object extObject = null; if (extObjectType != null && (extObject = Activator.CreateInstance(extObjectType)) != null) { arguments.AddExtensionObject(extObjectInfo.Namespace, extObject); } } } } transformSet = new XslTransformSet(metadata, transform, arguments); // If cache is enabled, place the transform instance and its metadata to the cache. if (transformCacheCollection != null) { foreach (var transformCache in transformCacheCollection) { transformCache.Put(transformName, transformSet); } } } } return(transformSet); } finally { TraceManager.WorkerRoleComponent.TraceOut(callToken); } }