Code:
/ 4.0 / 4.0 / untmp / DEVDIV_TFS / Dev10 / Releases / RTMRel / ndp / cdf / src / WF / RunTime / Hosting / SharedConnectionWorkflowTransactionService.cs / 1305376 / SharedConnectionWorkflowTransactionService.cs
#pragma warning disable 1634, 1691 //------------------------------------------------------------------------------ //// Copyright (c) Microsoft Corporation. All rights reserved. // //----------------------------------------------------------------------------- #region Using directives using System; using System.Transactions; using System.Diagnostics; using System.Collections; using System.Collections.Generic; using System.Collections.Specialized; using System.Configuration; using System.Threading; #endregion namespace System.Workflow.Runtime.Hosting { public class SharedConnectionWorkflowCommitWorkBatchService : WorkflowCommitWorkBatchService { private DbResourceAllocator dbResourceAllocator; private IDictionarytransactionConnectionTable; private object tableSyncObject = new object(); // Saved from constructor input to be used in service start initialization private NameValueCollection configParameters; string unvalidatedConnectionString; private bool _enableRetries = false; private bool _ignoreCommonEnableRetries = false; /// /// Enables the adding of this service programmatically. /// /// /// public SharedConnectionWorkflowCommitWorkBatchService(string connectionString) { if (String.IsNullOrEmpty(connectionString)) throw new ArgumentNullException("connectionString", ExecutionStringManager.MissingConnectionString); this.unvalidatedConnectionString = connectionString; } ////// Enables adding of this service from a config file. /// Get the connection string from the runtime common parameter section or the particular service parameter section /// of the configuration file, and instantiate a DbResourceAllocator object. /// /// /// public SharedConnectionWorkflowCommitWorkBatchService(NameValueCollection parameters) { if (parameters == null) throw new ArgumentNullException("parameters", ExecutionStringManager.MissingParameters); if (parameters.Count > 0) { foreach (string key in parameters.Keys) { if (0 == string.Compare("EnableRetries", key, StringComparison.OrdinalIgnoreCase)) { _enableRetries = bool.Parse(parameters[key]); _ignoreCommonEnableRetries = true; } } } this.configParameters = parameters; } #region Accessors internal string ConnectionString { get { #pragma warning disable 56503 if (this.dbResourceAllocator == null) { // Other hosting services may try to get the connection string during their initialization phase // (in WorkflowRuntimeService.Start) to dectect string mismatch conflict if (this.Runtime == null) throw new InvalidOperationException(ExecutionStringManager.WorkflowRuntimeNotStarted); this.dbResourceAllocator = new DbResourceAllocator(this.Runtime, this.configParameters, this.unvalidatedConnectionString); } #pragma warning restore 56503 return this.dbResourceAllocator.ConnectionString; } } public bool EnableRetries { get { return _enableRetries; } set { _enableRetries = value; _ignoreCommonEnableRetries = true; } } #endregion Accessors #region WorkflowRuntimeService override protected internal void Start() { WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "SharedConnectionWorkflowCommitWorkBatchService: Starting"); this.dbResourceAllocator = new DbResourceAllocator(this.Runtime, this.configParameters, this.unvalidatedConnectionString); if (this.transactionConnectionTable == null) this.transactionConnectionTable = new Dictionary(); // // If we didn't find a local value for enable retries // check in the common section if ((!_ignoreCommonEnableRetries) && (null != base.Runtime)) { NameValueConfigurationCollection commonConfigurationParameters = base.Runtime.CommonParameters; if (commonConfigurationParameters != null) { // Then scan for connection string in the common configuration parameters section foreach (string key in commonConfigurationParameters.AllKeys) { if (string.Compare("EnableRetries", key, StringComparison.OrdinalIgnoreCase) == 0) { _enableRetries = bool.Parse(commonConfigurationParameters[key].Value); break; } } } } base.Start(); } protected override void OnStopped() { WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "SharedConnectionWorkflowCommitWorkBatchService: Stopping"); foreach (KeyValuePair kvp in this.transactionConnectionTable) { kvp.Value.Dispose(); WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "Removing transaction " + kvp.Key.GetHashCode()); } this.transactionConnectionTable.Clear(); this.dbResourceAllocator = null; base.OnStopped(); } #endregion Public Methods #region Public Methods protected internal override void CommitWorkBatch(WorkflowCommitWorkBatchService.CommitWorkBatchCallback commitWorkBatchCallback) { // // Disable retries by default, reset to allow retries below if we own the tx DbRetry dbRetry = new DbRetry(_enableRetries); short retryCounter = dbRetry.MaxRetries; while (true) { // // When using LocalTransaction handle block access to the connection // in the transaction event handlers until all IPendingWork members have completed ManualResetEvent handle = new ManualResetEvent(false); Transaction tx = null; SharedConnectionInfo connectionInfo = null; try { if (null == Transaction.Current) { // // It's OK to retry here as we own the tx retryCounter = 0; // // Create a local, non promotable transaction that we share with our OOB services tx = new CommittableTransaction(); connectionInfo = new SharedConnectionInfo(this.dbResourceAllocator, tx, false, handle); } else { // // Can't retry as we don't own the tx // Create a dependent transaction and don't restrict promotion. tx = Transaction.Current.DependentClone(DependentCloneOption.BlockCommitUntilComplete); connectionInfo = new SharedConnectionInfo(this.dbResourceAllocator, tx, true, handle); } AddToConnectionInfoTable(tx, connectionInfo); using (TransactionScope ts = new TransactionScope(tx)) { try { commitWorkBatchCallback(); ts.Complete(); } finally { RemoveConnectionFromInfoTable(tx); // // Unblock transaction event handlers handle.Set(); } } CommittableTransaction committableTransaction = tx as CommittableTransaction; if (committableTransaction != null) committableTransaction.Commit(); DependentTransaction dependentTransaction = tx as DependentTransaction; if (dependentTransaction != null) dependentTransaction.Complete(); break; } catch (Exception e) { tx.Rollback(); WorkflowTrace.Host.TraceEvent(TraceEventType.Error, 0, "SharedConnectionWorkflowCommitWorkBatchService caught exception from commitWorkBatchCallback: " + e.ToString()); if (dbRetry.TryDoRetry(ref retryCounter)) { WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "SharedConnectionWorkflowCommitWorkBatchService retrying commitWorkBatchCallback (retry attempt " + retryCounter.ToString(System.Globalization.CultureInfo.InvariantCulture) + ")"); continue; } else throw; } finally { handle.Close(); if (tx != null) { tx.Dispose(); } } } } /// /// Get the SharedConnectionInfo object from the hashtable keyed by the transaction /// /// ///internal SharedConnectionInfo GetConnectionInfo(Transaction transaction) { return LookupConnectionInfoTable(transaction); } #endregion Public Methods #region Private Methods private void RemoveConnectionFromInfoTable(Transaction transaction) { lock (this.tableSyncObject) { SharedConnectionInfo connectionInfo; WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "TransactionCompleted " + transaction.GetHashCode()); if (transactionConnectionTable.TryGetValue(transaction, out connectionInfo)) { connectionInfo.Dispose(); this.transactionConnectionTable.Remove(transaction); } else { WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "TransactionCompleted " + transaction.GetHashCode() + " not found in table of count " + this.transactionConnectionTable.Count); } } } private void AddToConnectionInfoTable(Transaction transaction, SharedConnectionInfo connectionInfo) { lock (this.tableSyncObject) { this.transactionConnectionTable.Add(transaction, connectionInfo); WorkflowTrace.Host.TraceEvent(TraceEventType.Information, 0, "AddToConnectionInfoTable " + transaction.GetHashCode() + " in table of count " + this.transactionConnectionTable.Count); } } private SharedConnectionInfo LookupConnectionInfoTable(Transaction transaction) { lock (this.tableSyncObject) { return transactionConnectionTable[transaction]; } } #endregion Private Methods } } // File provided for Reference Use Only by Microsoft Corporation (c) 2007. // Copyright (c) Microsoft Corporation. All rights reserved.
Link Menu
This book is available now!
Buy at Amazon US or
Buy at Amazon UK
- ThrowOnMultipleAssignment.cs
- HtmlElementCollection.cs
- Metadata.cs
- CollectionDataContractAttribute.cs
- DesignerActionMethodItem.cs
- HttpModuleActionCollection.cs
- WebFormsRootDesigner.cs
- XPathDescendantIterator.cs
- SendKeys.cs
- RewritingSimplifier.cs
- ModelPerspective.cs
- XsltSettings.cs
- SelectionList.cs
- DocumentDesigner.cs
- controlskin.cs
- AssociationSetMetadata.cs
- DbProviderManifest.cs
- ISFTagAndGuidCache.cs
- XmlCustomFormatter.cs
- COM2IManagedPerPropertyBrowsingHandler.cs
- UnknownBitmapDecoder.cs
- GridViewSelectEventArgs.cs
- SystemResourceKey.cs
- AstTree.cs
- SnapshotChangeTrackingStrategy.cs
- TdsRecordBufferSetter.cs
- ParentControlDesigner.cs
- XmlTextReader.cs
- ModifierKeysValueSerializer.cs
- WebPartCatalogAddVerb.cs
- LineProperties.cs
- TrackingRecord.cs
- AliasGenerator.cs
- TdsParserHelperClasses.cs
- Certificate.cs
- BitmapEffectInput.cs
- SchemaElementDecl.cs
- SQLDecimalStorage.cs
- GetRecipientListRequest.cs
- Rectangle.cs
- Effect.cs
- FrameworkElementFactory.cs
- InstanceLockedException.cs
- EditorAttribute.cs
- HtmlUtf8RawTextWriter.cs
- ToolStripDropDown.cs
- Encoding.cs
- IdentityModelDictionary.cs
- PropertyGrid.cs
- NativeMethodsOther.cs
- FixedSOMTableRow.cs
- ProfileServiceManager.cs
- NGCSerializerAsync.cs
- PropertyInformation.cs
- Membership.cs
- ConfigurationValidatorBase.cs
- SourceInterpreter.cs
- BufferedStream2.cs
- ProfessionalColors.cs
- SystemPens.cs
- MemberDescriptor.cs
- ThousandthOfEmRealPoints.cs
- HttpBrowserCapabilitiesBase.cs
- DataGridParentRows.cs
- EmptyStringExpandableObjectConverter.cs
- ViewCellSlot.cs
- Function.cs
- WebPartConnectionCollection.cs
- ScriptResourceInfo.cs
- BrushValueSerializer.cs
- TemplateParser.cs
- DataRowIndexBuffer.cs
- versioninfo.cs
- DataControlCommands.cs
- UpdatePanel.cs
- ValueQuery.cs
- HttpPostProtocolImporter.cs
- UnitControl.cs
- ProcessHost.cs
- PrimitiveList.cs
- PackageDigitalSignature.cs
- XmlDataFileEditor.cs
- TdsParser.cs
- StrongNameSignatureInformation.cs
- IERequestCache.cs
- EntityDataSourceEntityTypeFilterConverter.cs
- WriterOutput.cs
- Inline.cs
- ListItemCollection.cs
- Utils.cs
- ProviderManager.cs
- TableCellCollection.cs
- OLEDB_Enum.cs
- HelpInfo.cs
- GridViewAutomationPeer.cs
- UpDownEvent.cs
- PathFigureCollection.cs
- NativeMethods.cs
- Int64.cs
- StringCollection.cs