How to build a temporary FeatureClass in ArcObject? - arcgis

I want to build a temporary FeatureClass which contains temporary Features , such as points, which are useless later in programming.
While, I searched for ArcObject API reference, but I can't find an efficient way to solve this problem. So how can I build temporary "container" to store some temporary Features ?
Should I first use CreateFeatureClass to build a real FeatureClass and later delete it? I don't think this method is cool for I have to deal with some CLSID thing.
PS:This "container" must have the ability to return a Cursor.

I think you should to use InMemoryWorkspace.
IWorkspaceFactory2 objWorkspaceFactory = new InMemoryWorkspaceFactoryClass();
IWorkspaceName objWorkspaceName = objWorkspaceFactory.Create(string.Empty, p_strName, null, 0);
IName objName = (IName)objWorkspaceName;
IWorkspace objWorkspace = (IWorkspace)objName.Open();
Now using this workspace you can to create Temprorary Feature Classes (perform search, get cursor and than delete the feature class).
I believe that in your case InMemory Workspace is more efficient than working with ShapeFile or Personal Geodatabase.

You can use the IScratchWorkspaceFactory2 interface, which is used to create temporary personal geodatabases in the temp directory. You can find this directory by looking at the %TEMP% environment variable. The scratch personal geodatabase will have the name mx.mdb where is the lowest positive number that uniquely identifies the geodatabase.
IScratchWorkspaceFactory2 factory = new ScratchWorkspaceFactoryClass();
var selectionContainer = factory.DefaultScratchWorkspace;

Related

SQL, Link to Element Feature

I have two classes. One Attribut of class1 is connected to another attribut of class2. This was done with the help of the context menue of the connector in the proximity of one class, it is called Link to element feature. The same is done on the other side of the connector to select the other attribut of the other class. So the connector directly connects two attributes and not the classes itselves. I havenĀ“t found the tables, where this infomation is stored, so I dont find the appropiate SQL to find connected (or not connected) attributes.
Here's the way for notes using Link to..
PDATA1 = 'Attribute'
PDATA2 = t_attribute.ID of the attribute
PDATA3 = name of the attribute
PDATA4 has 'Yes' (I don't recall what that's used for so you can probably ignore it
First SQL:
SELECT PDATA2 FROM t_object WHERE Object_Type='Note' AND PDATA1 = 'Attribute'
will give you the ID. Just put that in another SQL:
SELECT * FROM t_attribute WHERE ID = (above SQL)
and you have the attribute details. Or if you want to find the unmapped one just build a dissection with the found IDs from the first with the existing attribute IDs.
For associations using Link to... it's a bit more tricky. First off, any such connectors have the relevant information stored in t_connector.StyleEx like e.g.
LFEP={69A30E17-23AB-4641-9573-9BDBAA988D52}L;
LF<dir>P=<guid><pos>; connector is attached to attribute/operation
<dir> = S or E meaning Start (source) or End (target) <guid> = ea_guid of t_attribute or t_operation
<pos> is the edge (L or R) where the connector had been attached to in the moment when the link has been created. This is a superfluous information since the renderer will attach the link to whatever place is relevant.
There can be one LFSP, one LFEP or both be present in one StyleEx property
(from my Inside book)
Now you can filter that information with a SQL or (what I prefer) with a little script, since doing complex SQL string operations are not my expertise.

What is the right way to save the process instance id(s) created?

Using Camunda as the tool for orchestration of the microservices. At later time, I find the process_instances_id generated necessary for continuing a particular process by using it in messageEventReceived(). Code as follows:
val processid = getProcessID(key1, key2)
val runtimeService = processengine.getRuntimeService
val subscription = runtimeService.createEventSubscriptionQuery
.eventType("message")
.eventName(eventname)
.processInstanceId(executionid)
.singleResult
runtimeService.messageEventReceived(subscription.getEventName, subscription.getExecutionId)
As of this moment the processid is saved and then retrieved from the database using the getProcessID(...) function when necessary. Is this proper?
Does camunda already have the list of process_ids in its own database? If so, how do I retrieve a particular process instance id just giving composite key(s)? Is that even possible?
It is the common way. You can also use the public api to get the process instance and his id via the process definition key.
See the following example from the documentation:
runtimeService.createProcessInstanceQuery()
.processDefinitionKey("invoice")
.list();
For your given example there is also a simpler way. It is possible to correlate the message via the runtime service.
See this example from the documenation:
runtimeService.createMessageCorrelation("messageName")
.processInstanceBusinessKey("AB-123")
.setVariable("payment_type", "creditCard")
.correlate();
You can use
runtimeService.createProcessInstanceQuery().list();
the query supports fluent criteria for filtering, for example on process_key, variables, businessKey ...

How to access key-value Lookup through the API in GoodData?

In GoodData's ETL tool there's a key-value store that one can use for keeping some kind of state between ETL runs: http://developer.gooddata.com/cloudconnect/manual/lookup-table-functions-ctl2.html
Is there a way how to set / read these values through the REST API?
There is something called project metadata. It holds metadata on a per project level. It is what you can see if you go to Project explorer in CloudConnect and look at customer properties.
The data can be read like this
GET /gdc/projects/<projectName>/dataload/metadata
You can read only particular key
GET /gdc/projects/<projectName>/dataload/metadata/<key>
And update an existing key
PUT /gdc/projects/<projectName>/dataload/metadata/<key>
Also delete
DELETE /gdc/projects/<projectName>/dataload/metadata/<key>
Or create a new on
POST /gdc/projects/<projectName>/dataload/metadata/ {"metadataItem" : {"key" : "some_key", "val" : "some_val"}}
Another way is to use GoodData ruby SDK (https://github.com/gooddata/gooddata-ruby/)
client = GoodData.connect('username', 'pass')
project = client.projects('project_id')
project.metadata
metadata.inspect
You can also set the metadata liek this
project.set_metadata('key', 'val')

Checking if certain key exists in database

I have saved certain MDX query and I run them using ADOMD.NET. I get CellSet back which I convert into dataset. All this is working fine. Now the DB team has changed the cube structure. They have updated the DimesnionName, Attribute Name etc. Some dimensions got renamed and some got deleted. Becuase of this I am unable to run my saved queries. I want to create a console application, which will take list of keys ([DimensionName].[AttributeName] or [DimensionName].[AttributeName].[MemeberName] format) and it will tell me following keys does not exists.
Please let me know if this is possible programatically. I dont want to check it manually.
Kindly share a link or code which will help me acheive this.
Thank you.
If you're using ADOMD already this should be no problem, just use the metadata queries:
http://msdn.microsoft.com/en-us/library/ms123485.aspx
Alternatively, AMO is nice http://msdn.microsoft.com/en-us/library/microsoft.analysisservices.aspx
I use it in SSIS for processing, you could easily use it in .Net to test existence of elements:
using Microsoft.AnalysisServices;
...
Server server = new Server();
server.Connect(cubeConnectionString);
Database database = server.Databases.FindByName(databaseName);
Cube cube = database.Cubes.FindByName(cubeName);
foreach (MeasureGroup measureGroup in cube.MeasureGroups)
{
foreach (Partition partition in measureGroup.Partitions)
{
...
}
}
foreach (CubeDimension cubeDimension in cube.Dimensions)
{
Dimension dimension = cubeDimension.Dimension;
var dimName = dimension.Name;
...
}
Finding the names in advance for all the elements you need is probably the hard part (And keeping it all up-to-date).
Would it not be easier to fire all the queries at the cube and try to trap the "no such thing" response?

Tridion 2011 - Engine.GetObject overloads

I found the following difference between the old VBScript API and the .Net API:
In the old VBScript API it's possible to invoke "TDSE.getObject" to retrieve a Tridion object passing by the webdav path, an integer to select how to open it (read only, read and write, etc) and the ID of the publication where there is the exact element of the blueprint we want.
In the new .Net API all I found was "Engine.GetObject" but it only receives the TCM ID or the webdav path of an element.
Our scenario is the following; in the old VBScript code, this overload of the getObject method was used to avoid some permission issues detected while using TCM IDs instead of the webdav paths and because it's much more handful when you need to copy the code between different environments (see DEV, PREPROD and PROD for example), avoiding changing TCM IDs.
So my questions are:
Is there and overload like the old one in the new .Net API?
If not, is there a way of retrieving items by webdav keeping in mind that some of them could be localized and changed from their parent? (the old way works with this, if you send the root webdav path it will retrieve local objects even if their names aren't exactly the same as the parents)
Thank you!
Do you want to be able to use the webdav url of the top-level item, and specify the publication id from which to get the item?
I would create an extension method on Engine that does this for you:
public static T GetObject<T>(this Engine engine, string webDavUrl, int publicationId)
where T : IdentifiableObject
{
[logic to retreive the item and then if needed
get the correct tcm uri and get the intended item]
return item as T;
}
However, this is quite an expensive operation since you get two objects instead of one. So I dont know if I would use this method very often.
Here some samples
IdentifiableObject item = engine.GetObject(new TcmUri("tcm:5-677"));
//will give you the latest approved version in the publication 5.
IdentifiableObject item = engine.GetObject(new TcmUri("tcm:5-677-v0"));
//will give you the WF or Editable version.
TcmUri uri = new TcmUri("tcm:5-677");
uri.PublicationId = 6;
IdentifiableObject item = engine.GetObject(uri);
//will give you the latest approved version in the publication 6.
Engine.GetObject has 4 overloaded method.
GetObject(Session, string)
GetObject(string)
GetObject(TcmUri)
GetObject(Item)
You can check the Tom.Net Api for more details.
Actually, using Engine.GetObject Method (String) should work.
public virtual IdentifiableObject GetObject(
string itemUriOrWebDavUrl
)
You can do something in this way:-
Get the Object based on WebDav URL
Get the TCM ID from this object
Based on your publication, modified your TCM ID accordingly and do your stuff
OR
Try something this way too:-
Repository testRepository = (Repository)session.GetObject("tcm:0-2-1");
Component testComponent = (Component)testRepository.GetObject(webdavURL); //Assuming actual TCM ID is "tcm:1-3"
Console.WriteLine(testComponent.Id); // should show "tcm:2-3"
// Do Your Other Stuff