-
Notifications
You must be signed in to change notification settings - Fork 0
Scenario Conventional Attachments
It is common in Clarify to attach files to entities in the system.
Agent has a built in facility for conventionally providing support for uploading attachments and having them related to a given Entity. For baseline Clarify entities this is pretty straight forward. If you wish to use this mechanism for your custom entities you'll have to do a bit of extra work which we will discuss.
We start with a Model representing the entity to which we want to add attachments. We will be using a marker interface to annotate our model and enforce that required properties are present. I'll be using the SitePart baseline entity to illustrate how this is done. This entity currently supports attachments in Agent so you can always look at the source code for more details.
public class SitePart : DomainEntity, IAttachableDomainEntity
{
//... properties for the model
}If your model will use a string based identifier and not a Clarify objid. You'll need to add another marker interface IHasNaturalKey. This will prevent Agent from treating your identifier as an integer. Take a look at IWorkflowEntity for an example of this in use.
We need to register our attachable domains with the IoC container. Below is an example registration against the custom bottle included with Agent.
public class customStructureMapRegistry : Registry
{
public customStructureMapRegistry()
{
Scan(scan =>
{
scan.TheCallingAssembly();
scan.ConnectImplementationsToTypesClosing(typeof(ModelMap<>));
scan.ConnectImplementationsToTypesClosing(typeof(IFilterMap<>));
scan.AddAllTypesOf<IAttachableDomainEntity>();
scan.WithDefaultConventions();
});
}
}Also, your assembly will need to reference the Dovetail.SDK.Attachments assembly.
Agent's conventional entity actions need to have the ability to retrieve one of your entities. This is handled by defining a ModelMap for your entity.
public class SitePartMap : ModelMap<SitePart>
{
protected override void MapDefinition()
{
FromView("site_part")
.Assign(d => d.DatabaseIdentifier).FromIdentifyingField("objid")
.Assign(d => d.Id).BasedOnField("objid").Do(v => v)
// elided for brevity
}
}It is important to always define a FromIdentifyingField property so your modelmap knows how to retrieve an object by id.
As always you need to ensure your model map is registered with the IoC container.
scan.ConnectImplementationsToTypesClosing(typeof(ModelMap<>));Build and launch your web application and visit the FubuMVC Diagnostics. http://localhost:25120/_fubu/endpoints
You should see a GET and POST route for uploading attachments to a given site part:
/siteparts/{Id}/upload. The GET route in this case does not do much. It returns a valid POST url. This pattern is followed for all conventional entity actions. The GET gives you context you may need to do the action and the POST route does the action.
Now that your endpoint is all setup all that is left is your front end. Effectively all you need on the front end is a form with a file input named Files.
<form action="http://localhost:25120/siteparts/268435457" method="POST" enctype="multipart/form-data">
<label for="Files">Upload a animal attachment</label>
<input id="Files" type="file" name="files[]" multiple />
<input type="submit" value="Upload"/>
</form>When you are not using a Clarify baseline entity the Dovetail SDK needs to know some metadata about your custom entity. Our attachment code will use this metadata to know how to do attachment database operations.
To give Dovetail SDK this metadata you'll be implementing the IWorkflowObjectMetadata interface.
public interface IWorkflowObjectMetadata
{
string Alias { get; set; } //name of your entity
WorkflowObjectInfo Register();
}And as always you'll need to register all implementations of this interface with the IoC container.
scan.AddAllTypesOf<IWorkflowObjectMetadata>();The Register method returns a WorkflowObjectInfo instance which is a type used by DovetailSDK for, you guessed it, workflow operations. In our case we only care about populating a few values of this object for attachment purposes.
public class Animal : DomainEntity, IAttachableDomainEntity
{
// properties
}
public class AnimalWorkflowObjectMetadata : IWorkflowObjectMetadata
{
public string Alias { get { return ""; } }
public WorkflowObjectInfo Register()
{
return new WorkflowObjectInfo("animal") {
IDFieldName = "name",
ActivityRelation = "act_entry2animal",
AttachmentRelation = "animal2doc_inst",
TimeStampFieldName = "modify_stmp"
};
}
}It is important to highlight that the name of our custom model Animal needs to match the WorkflowObjectInfo's ObjectName which is the constructor argument for the new WorkflowObjectInfo. If for some reason you wish your model name to be different you can use the Alias. Traditionally the object name is the same as the database table name.
Your entity needs to have a relation traversing between its base table and the doc_inst table. For example your custom entity with a base table of 'animal' should have a relation animal2doc_inst.
Your entity needs to have a relation traversing between act_entry and your entity's base table. For example if your custom entity with a base table of 'mineral' should have a relation of mineral2act_entry and the WorkflowObjectInfo's ActEntryRelation should be act_entry2animal.
You should leave this field blank if your identifier is simply objid.
Check your ModelMap and see what field is being used to populate your Id property. If this field is populated by anything other than objid you'll need to make the IdFieldName property of the WorkflowObjectInfo match the field populating your Id property.
If your entity has a timestamp field which you wish to have updated when an attachment is added you need to populate the TimeStampFieldName property.
If your entity does not use objid as the field that populates the Id property. You'll need to add the marker interface IHasNaturalKey to your Model object. This marker informs an infrastructure piece EntityFinder that the key is not an ObjId.
I created this gist which compiles all the changes needed to create a custom entity and have it support attachments.
We hope you enjoyed this helpful Agent training document. If you see an error or omission please feel free to fork this repo to correct the change, and submit a pull request. Any questions? Contact Support.

