How can I enter a workflow at an arbitrary step - workflow-foundation-4

I have a workflow service that links a Workflow Foundation 4 process with an application database which stores records that show what step our users must complete next. In the event of a non-resumable error in the workflow, it will make it so that the workflow is unable to be resumed, but the database entries that are in the application still exist, so there is a "disconnect" between workflow state and our application state.
What I would like to do is create another instance of the failed workflow, but get it into sync with the application database entries. That would entail going to an arbitrary entry point in the workflow based on the application database entries that exist.
Is it possible to do this? Are there any pitfalls to doing so? Is there a better way to manage the workflow to application dependency?
The workflow would look something like this:
Start the workflow. This creates an application db record that tracks the progress of the process and a db record that shows the user what needs to be done next.
The user "works" the step, which does a call into the workflow service (using receive/sendreply), updating the db record with the outcome of the work, and moving to the next step in the workflow.
Step 2 repeats with all the various steps creating db records to be worked, then updating those records with the results of being worked and creating new db records to be worked, until the process completes.
The question I'm trying to answer is if the user gets to a certain step in the process and the workflow engine fails so that the workflow instance is not resumable, how might I use the application db entries to "restart" the process to re-enter the process, skipping to the point of failure (assuming we had resolved the issue that caused the failure in the first place). This would eliminate the user having to "redo" work that had already been done, and stay in the process.
What I thought was that if there was a way of looking at the application database records that have been created to determine where the process had died, if I could "skip" previously finished steps and move to the point in the workflow that failed based on those db records, I could "resume" the process (from the user's point of view) without causing rework.

I'm just starting out with Workflow and I've been watching some videos on channel9 at MSDN and I came across one that may help you out.
It talks about using Bookmarks and some Task based-API by Ron Jacobs.
Check it out at: Workflow TV - WF4 Workflow Episodes - a Task Based API

It sounds like what you want to implement is Compensation- that is, custom rollback functionality built into a transaction. Here's the start of the Transaction and Compensation activity documentation:
http://msdn.microsoft.com/en-us/library/ee358756.aspx
You can use the Compensate activity to do database cleanup after a failed transaction.

Related

Long Running task from asp.net web application (Only on user action)

I need to run a long running task like report export, report import feature which will take few minutes to hour to complete the task. I want to start the task as soon as user gives command from the asp.net mvc view.
I found various web portals, but I couldn't find the exact solution I was looking for or might be I didn't got their idea (or, limited by my experience). I don't need something that runs at certain time interval or at certain time-stamp of the day/week. I only need the background job to be executed on user request and update the task as completed in DB after it's done. So, the background job need to be always triggered by user only.
I assume the ideal solution will be something like, Background service/job is always in ready state to accept trigger from my web application in some kind of port and as soon as it receives command from web application, it (a) either send everything to job when requested for action (b) or, just poke job to start its task (based on the updated db table entry made just before the call action) . So, the user can browse through other pages in the application and can view the progress of all such tasks in one of the view (where he can even cancel or see the completed task). Note, that there can be simultaneous request for the job from different web users which should be treated as separate job (As data export differs based on user access-rights).
I want to go with the simple method, with 100% assurance of task to be done/not done as recorded in db (no crashing of service). What are the best approaches (except azure jobs) as i want to implement the service within same server and I have access to the server/virtual machine to install windows services/packages if needed.
Take look at this great article that Hanselman wrote:
How to run Background Tasks in ASP.NET
Also Hangfire is a mature library that can make development of application long running process more easy.
Hangfire is an open-source framework that helps you to create, process and manage your background jobs, i.e. operations you don't want to put in your request processing pipeline

ASP.NET OLTP App - creating new version of records

My question is same as this question - but a little to add on to it. My problem is that the users of my web app are allowed to create new versions of a record. Every new version of a record results in creating corresponding "new versions" in 50 other related tables to record individual changes to that particular version. This creation of a new version with about 50 tables involved is running within a transaction (to rollback all changes in the event of an error). Many a times this procedure is slow, understandably due to a "lengthy transaction" with too many table "insertions" involved.
I am looking at a better solution/design to implement such a scenario.
Is there a better way to maintain "versions" of the same record, particularly when it creates too many duplicates in multiple tables
I don't feel the design in itself is good with too many records getting inserted for "every row version", but would at least like to address the immediate problem, the "lengthy transaction" - which causes delay at times. There may not be way way out, but wanted to still ask out - If I don't put the "versioning" inside a transaction, is there a better way to rollback in the event of an error (because transaction appears to block other OLTP queries - due to inserting new versions on all primary tables)
The versioning query runs for about 10 seconds right now, but gets worse at times. Any thoughts are appreciated
Do you have to return the "created" or "failed" message in real time? The following might also be overkill for your solution but it does create a scalable solution.
The web-server could post a message (to a queue of some sort) requesting the action. At this point the user could continue using the site to do other stuff. A windows service in the background can process the message (out of context of the website) and then notify the user (by a message inside the website, similar to stack overflow notifications) or by email that the task has either run or failed.
If you can get away with doing processing decoupled in near real time then you can modify your windows service to scale. You can have a thread pool to manage requests - so maybe you only have 5 threads running at any one time to limit load. If you run into more performance problems you can scale out and develop a system that can have 2 or more processors of the queue (that does add it's own problems / complexity).

TSQL + ASP MVC - Schedule ASPX or DB_SCHEDULE?

We are developing huge CRM application: MSSQL + ASP MVC. We've created views for password reminder. Every time user want to remind his password application generates GUID. This GUID is deleted when user get his new password. So for sure there are going to be some "lost GUIDs" in the database - GUIDs created for users that will never finish do recover password.
I want to schedule a job or app that will delete those "lost GUIDs". Is it better do accomplish by:
1. setting a job in the database,
or by
2. writting another controller and scheduling it
?
In my opinion database job is better solution, because it put data-workflow focused on database, but I prefer to as experts here :).
Which solution will be more scalable and easyer to deploy over number of clients?
"Better" is subjective and I usually handle different tasks differently.
I have always written these types of tasks as a job. More specifically, the applications that I have built that follow a similar model always have app specific daily/weekly/monthly tasks. For this type of task, I bunch it together with other jobs in a wrapper proc.
I don't manage all jobs this way as, more important things I want to take full advantage of sql agent's notifications and such but general regular data cleanup tasks will log an error and rerun the next cycle, which is acceptable for me.
I hope this helps!

Dealing with Long running processes in ASP.NET

I would like to know the best way to deal with long running processes started on demand from an ASP.NET webpage.
The process may consist of various steps (like upload files to the server, run SSIS packages on them, execute some stored procedures etc.) and sometimes the process could take up to couple of hours to finish.
If I go for asynchronous execution using a WCF service, then what happens if the user closes the browser while the process is running, how the process success or failure result should be displayed to the user? To solve this, I choose one-way WCF service calls, but the problem with this is I need to create a process table and store the result (and error messages if it fails in any of the steps and which steps have completed successfully) in that table which is an additional overhead because there are many such processes with various steps that the user can invoke from the web page and user needs to be made aware of the progress (in simplest case, the status can be "process xyz running") and once it is done, the output needs to be displayed to the user (for example by running a stored procedure).
What is the best way to design the solution for this?
As I see it, you have three options
Have a long running page where the user waits for the response. If this is several hours, you're going to have many usability problems, so I wouldn't even consider it.
Create a process table to store the results of operations. Run service functions asynchronously and delegate logging the results to the service. There can be a page that the user refreshes which gets the latest results of this table.
If you really don't want to create a table, then store all the current process details in the users' session state, and have a current processes page as above. You have the possible issue that the session might timeout, or the web app might restart and you'll lose all this.
I can't see that number 2 is such a great hardship. You could make the table fairly generic to encompass all types of processes: process details could just be encoded as binary or xml and interpreted by the web application. You then have the most robust solution.
I cant say what the best way would be but using Windows Workflow Foundation for such long running processes is definitely one way to go about it.
You can do tracking of the process to see what stage it is at, even persist it if you have steps where it is awaiting user input etc.
WF provides a lot of features out of the box (especially if your storage medium is SQL Server) and may be a good option to consider.
http://www.codeproject.com/KB/WF/WF4Extensions.aspx might help give you some more insight into the same.
I think you are in the right track. You should run the process asynchronously, store the execution somewhere (a table), and keep status of the running process in there.
Your user should see a pending display label while the process is executing, and a finished label with the result when the process finished. If the user closed the browser, she will see the result of her running process next time she logs in.

Listing Currently Running Workflows in .Net 4.0

I've got a .Net 4.0 Workflow application hosted in WCF that takes a request to process some information. This information is passed to a secondary system via a web service and returns a bool indicating that its going to process that information.
My workflow then loops, sleeping for 5 minutes and then querying the secondary system to see if processing of the information is complete.
When its complete the workflow finishes.
I have this persisting in SQL, and it works perfectly.
My question is how do I retrieve a list of the persisted workflows in such a way that I can tie them back to the original request? I'd like my UI to be able to list the running workflows in a grid with the elapsed time that they've been run.
I've thought about storing the workflow GUID in my primary DB and generating the list that way, but what I'd really like is to be able to reconcile what I think is running, and what the persistant store thinks is running.
I'd also like to be able to select a running workflow and kill it off or completely restart it if the user determines that its gone screwy.
You can promote data from the workflow using the SqlWorkflowInstanceStore. The result is they are stored alongside the workflow data in the InstancesTable using the InstancePromotedPropertiesTable. Using the InstancePromotedProperties view is the easiest way of querying you data.
This blog post will show you the code you need.
Another option, use the WorkflowRuntime GetAllServices().
Then you can loop through each one to pull out the data you need. I would cache the results, given this may be an expensive operation. If you have only 100 or less running workflows, and only a few users on your page, don't bother caching.
This way you don't have to create a DAL or Repo layer. Especially if you are using sql for persistence.
http://msdn.microsoft.com/en-us/library/ms594874(v=vs.100).aspx

Resources