I changed the SQL Server Authentication settings to Windows Authentication Mode. But when I login to Creatio I get a Login Failed error.

What do I need to set in the Connection String?

 

Like 0

Like

1 comments

I want to update MaxFileSize and ActiveFileContentStorage using a query to save time. But whenever I tried to run the query from SQL Console it successfully update the values in the database but they are not reflected in the Creatio Portal.

 

When I add the query in the SQL file in advanced settings and run it, it updates the data in the database and in the portal as well. The problem is that it's not dynamic which will kill the purpose of using the query.

 

In other words, if I have to go and change the value in that file and run it again then we can do the same for the system settings as well.

 

Can anyone help me with that?

 

Thanks in advance.

Like 0

Like

1 comments

Hello Syed,

 

The issue here is that these values are also storred in cache and direct updating of these values are not reflected in the cache. That's why you have old values after updating values from the database directly.

 

What should be done after updating values in the database is Redis flush. But this will lead to all users to be logged out from the system and obviously cannot be performed during business hours for the application (or users should be notified that the Redis will be flushed soon). After Redis flush new system settings values will be used when working in the application.

Show all comments

Hi all, 



I am trying to figure out, how do we connect Creatio directly to another (webapp's/app) SQL database which is not the Creatio one, without needing to pass through an API.

 

If we keep it simple, Pipedrive, they are able to provide SQL connections through Zapier, with triggers on both sides (if a change in Pipedrive --> add a column in the other SQL db OR if column added in SQL DB, do x action in Pipedrive). https://zapier.com/apps/pipedrive/integrations/sql-server 



How do we replicate such direct (bi-directional) integration with Creatio and another sql db without the need for the other web app to expose or call an API ?



Cheers, 



Damien

Like 2

Like

1 comments

Hi Damien,

If I understood your question correctly, I recommend you look at this discussion.

As described there, the most suitable solution, in this case, is a business process.

Show all comments

Hello Creatio Community,

This happens in the Application Section. When i fill in the product terms and try to save the Application this pop up is shown. Meanwhile the object SysFinApplicationSpecRight doesnt exist at all in the database. How can I fix this problem ?

Regards

Like 0

Like

2 comments

Printscreen of Error Logs

 

Managed to solve the problem by re-compiling FinApplicationSpec

Show all comments

Hi community,

 

I'm working on a new view object to create custom dasboards for my customer based on Bulk Email stats. I noticed that Creatio has an OOTB View object called "VwBulkEmailAudience" which is based on "BulkEmailTarget", "BETArchiveFirstGeneration" and "BETArchiveSecondGeneration".

Does anybody knows what the least two tables are used for? I have checked both the local-dev and the production site, and those tables are empty.

I enclose the script for the OOTB View in case you'd like to gain a better understanding of what I'm talking about.

 

Thank you in advance guys and girls! Have a nice day :)

-- View: public."VwBulkEmailAudience"
 
-- DROP VIEW public."VwBulkEmailAudience";
 
CREATE OR REPLACE VIEW public."VwBulkEmailAudience" AS
 SELECT "BET"."MandrillId" AS "Id",
    "BET"."CreatedOn",
    "BET"."ModifiedOn",
    "BET"."BulkEmailId",
    "BET"."ContactId",
    "BET"."EmailAddress",
    "BERR"."DCReplicaId" AS "ReplicaId",
    "BET"."LinkedEntityId",
    "BET"."BulkEmailResponseId",
    "BET"."Clicks",
    "BET"."Opens",
    "BET"."ProviderName",
    NULL::text AS "SessionId",
    0 AS "IsSent"
   FROM "BulkEmailTarget" "BET"
     LEFT JOIN "BulkEmailRecipientReplica" "BERR" ON "BERR"."RecipientId" = "BET"."MandrillId"
UNION ALL
 SELECT "FG"."MandrillId" AS "Id",
    "FG"."CreatedOn",
    "FG"."ModifiedOn",
    "FG"."BulkEmailId",
    "FG"."ContactId",
    "FG"."EmailAddress",
    "BERR"."DCReplicaId" AS "ReplicaId",
    "FG"."LinkedEntityId",
    "FG"."BulkEmailResponseId",
    "FG"."Clicks",
    "FG"."Opens",
    "FG"."ProviderName",
    NULL::text AS "SessionId",
    0 AS "IsSent"
   FROM "BETArchiveFirstGeneration" "FG"
     LEFT JOIN "BulkEmailRecipientReplica" "BERR" ON "BERR"."RecipientId" = "FG"."MandrillId"
UNION ALL
 SELECT "SG"."MandrillId" AS "Id",
    "SG"."CreatedOn",
    "SG"."ModifiedOn",
    "SG"."BulkEmailId",
    "SG"."ContactId",
    "SG"."EmailAddress",
    "BERR"."DCReplicaId" AS "ReplicaId",
    "SG"."LinkedEntityId",
    "SG"."BulkEmailResponseId",
    "SG"."Clicks",
    "SG"."Opens",
    "SG"."ProviderName",
    NULL::text AS "SessionId",
    0 AS "IsSent"
   FROM "BETArchiveSecondGeneration" "SG"
     LEFT JOIN "BulkEmailRecipientReplica" "BERR" ON "BERR"."RecipientId" = "SG"."MandrillId";
 
ALTER TABLE public."VwBulkEmailAudience"
    OWNER TO puser;

 

Like 0

Like

2 comments
Best reply

Hi Federica,

The "BETArchiveFirstGeneration" and "BETArchiveSecondGeneration" tables have been added in the 7.17.1 version of Creatio. They are used as a way to archive old records from the BulkEmailTarget table. Records older than 1 year go into those tables.

To get information about the OLD licenses usage you would need to use the VwBulkEmailTarget view as it looks into both the BulkEmailTarget and BETArchive tables. 

 

Best regards,

Max.

Hi Federica,

The "BETArchiveFirstGeneration" and "BETArchiveSecondGeneration" tables have been added in the 7.17.1 version of Creatio. They are used as a way to archive old records from the BulkEmailTarget table. Records older than 1 year go into those tables.

To get information about the OLD licenses usage you would need to use the VwBulkEmailTarget view as it looks into both the BulkEmailTarget and BETArchive tables. 

 

Best regards,

Max.

Thank you very much Max for clarifying! :)

Show all comments

hi all,

 

I need the to enable the SQL query console but I can't find the SQL executer and can't find the option "SQL query console" in operation permissions 

 

any sol?

 

thanks 

Like 0

Like

4 comments

Hi Ibrahim,

 

Unfortunately, the SQL query console plugin is not supported anymore. As of now there are no alternatives but we are working on creating one. You can send the scripts you need to execute to our support address support@creatio.com and we will run them for you!

 

Best regards,

Max.

I am currently working on a new marketplace add-on for this as well.

For now, if you have the previous SQL Executor add-on in another system, you can export the package from the configuration to install into another system.

Ryan

Ryan Farley,

wondering if you have already created something useable, because the old SQL console is not really working anymore in the latest releases.

 

I'd be happy to contribute either with testing or development!

 

Thanks for your effort!

Ryan Farley,

Ditto, I'd be happy to contribute either with testing or development!

Show all comments

Hello community,

I am implementing a way to import/export organizational data. The thing I want to do is create a business process that will transfer the data from SysAdminUnitCopy to SysAdminUnit and vice versa.  For the transfer of this data I created a script in sql server which transfers this data and executes successfully.

The next thing i need to do now is put this script in a sql script type schema and call it from a process.

Is there any way to call/execute a sql script schema from a business process?

 

Like 0

Like

1 comments

Hi community,

 

When implementing a web service, I have a GET method with a parameter :

 

public int GetMethod(string name)

 

In this method, I did a query to get the age of the person in parameter :

 

var select = new Select(UserConnection)

     .Column("Age")

     .From("Contact")

     .Where("Contact", "Name").IsEqual(Column.Parameter(name)) as Select;

 

Then I save the age into an int var :

 

var age = select.ExecuteScalar();

 

return age;

 

The problem is the following :

 

How can I check if the name of a contact in the method parameter exsists in the DB or not ?

 

Example :

 

if(name != exists) {

   return 0;

} else {

  return age;

}

 

Thanks a lot.

 

Best regards,

Jonathan

Like 0

Like

4 comments
Best reply

Hi Jonathan,

 

Usually you use dataReader to get the value from your select query. What you can do is:

bool hasRecord = false;
using (DBExecutor executor = UserConnection.EnsureDBConnection()) {
using (IDataReader dataReader = select.ExecuteReader(executor)) {
  while (dataReader.Read()) {
    hasRecord  = true;
  }
 }
}
if(hasrecord){
  return age
}else{
  return 0
}

Or you can just set the default value of the age =0. Therefore if the dataReader does not return any record, the default value age (0) will be returned.



regards,

Cheng Gong

Hi Jonathan

 

Please add the next using -     

     using Terrasoft.Common;   

on the top of the page(if you didn't have this one). 

 

Then in the part of the code when you are trying to retrieve the age:

 

if (name.IsNullOrEmpty())

{

return 0;

}

else

{

return age;

}

 

Best Regards, 

 

Bogdan L.

Hi Jonathan,

 

Usually you use dataReader to get the value from your select query. What you can do is:

bool hasRecord = false;
using (DBExecutor executor = UserConnection.EnsureDBConnection()) {
using (IDataReader dataReader = select.ExecuteReader(executor)) {
  while (dataReader.Read()) {
    hasRecord  = true;
  }
 }
}
if(hasrecord){
  return age
}else{
  return 0
}

Or you can just set the default value of the age =0. Therefore if the dataReader does not return any record, the default value age (0) will be returned.



regards,

Cheng Gong

Bogdan Lesyk,

Thanks for your answer. It helped a lot !

Cheng Gong,

 

Your answer is really perfect ! Thanks a lot, i'll definitely save this snippet of code for my future implementations.

 

Regards,

Jonathan

Show all comments

In the cloud version, is it possible to remove "SQL query console" menu item from System Designer without losing the ability to use SQL Executor? I mean setting Access to “SQL query console” section permission to No won't solve the question, because it will deny access to SQL Executor, while I want just to remove the link from UI, keeping the ability to use the tool in requests.

Like 1

Like

1 comments
Best reply

If you want to remove it completely:

1) Make sure your package has Samarasoft.SqlConsole as a dependency (or add this in Custom package)

2) Create a replacing view model and select parent "SystemDesigner"

3) Add this code:

define("SystemDesigner", [], function() {
	return {
		diff: [
			{
				"operation": "remove",
				"name": "SqlConsoleLink"
			}
		]
	};
});

If you want to only show it for the Supervisor user, do steps 1 & 2 above, but use this code instead:

define("SystemDesigner", [], function() {
	return {
		attributes: {
			"IsSqlConsoleVisible": {
				dataValueType: Terrasoft.DataValueType.BOOLEAN
			}
		},
		methods: {
			init: function() {
				this.callParent(arguments);
				this.set("IsSqlConsoleVisible", 
					Terrasoft.SysValue.CURRENT_USER_CONTACT.displayValue === "Supervisor"
				);
			}
		},
		diff: [
			{
				"operation": "merge",
				"name": "SqlConsoleLink",
				"values": {
					"visible": { "bindTo": "IsSqlConsoleVisible" }
				}
			}
		]
	};
});

Ryan

If you want to remove it completely:

1) Make sure your package has Samarasoft.SqlConsole as a dependency (or add this in Custom package)

2) Create a replacing view model and select parent "SystemDesigner"

3) Add this code:

define("SystemDesigner", [], function() {
	return {
		diff: [
			{
				"operation": "remove",
				"name": "SqlConsoleLink"
			}
		]
	};
});

If you want to only show it for the Supervisor user, do steps 1 & 2 above, but use this code instead:

define("SystemDesigner", [], function() {
	return {
		attributes: {
			"IsSqlConsoleVisible": {
				dataValueType: Terrasoft.DataValueType.BOOLEAN
			}
		},
		methods: {
			init: function() {
				this.callParent(arguments);
				this.set("IsSqlConsoleVisible", 
					Terrasoft.SysValue.CURRENT_USER_CONTACT.displayValue === "Supervisor"
				);
			}
		},
		diff: [
			{
				"operation": "merge",
				"name": "SqlConsoleLink",
				"values": {
					"visible": { "bindTo": "IsSqlConsoleVisible" }
				}
			}
		]
	};
});

Ryan

Show all comments

Dear Community,

 

I am using EntityEventListener to update a connected record of a records before deleting it using the following method:

public override void OnDeleting(object sender, EntityBeforeEventArgs e)

But when deleting the record it says there is connected records, I think this is linked to the count I am doing to check the number of records that match a condition.

 

Here the full code :

[EntityEventListener(SchemaName = "Activity")]
public class ActivityEventListener : BaseEntityEventListener
{
 
        public override void OnDeleting(object sender, EntityBeforeEventArgs e)
        {
                base.OnDeleting(sender, e);
                Entity activity = (Entity)sender;
                var userConnection = activity.UserConnection;
	        var accountId = activity.GetTypedColumnValue<Guid>("AccountId");
                var activityId = activity.GetTypedColumnValue<Guid>("Id");
                int count = CountNumberOfActivityRdv(accountId, userConnection);
	        Guid ContactClientOuRepresentantNon = new Guid("f550b45d-093e-43ba-bdd1-bc0bd43c8e16");
 
	        if (count > 0)
	        {
                        var update = new Update(userConnection, "Account")
                            .Set("ContactClientOuRepresentantId", Column.Parameter(ContactClientOuRepresentantNon))
                            .Where ("Id").IsEqual(activityId.ToString());
                        update.Execute();
	        }
        }
 
        public int CountNumberOfActivityRdv(Guid accountId, UserConnection userconnection)
        {
	        int count = 0;
                var select = new Select(userconnection)
                        .Column(Func.Count("Id"))
                    	.From("Activity")
                        .Where("ActivityCategoryId").IsEqual("42c74c49-58e6-df11-971b-001d60e938c6")
                	.And("AccountId").IsEqual(accountId.ToString()) as Select;
 
                count = select.ExecuteScalar<int>();
 
	        return count;
        }

 

Do I have to clear the cache or set the select to null ?

Like 0

Like

8 comments
Best reply

Oscar Dylan,

 

I've done it differently, when deleting the activity I send a message with the accountId linked to the activity deleted, and I catch it in the account edit page to do the necessaries processing. I had no problem with this method. Here is the code I've made for the sake of it.

onActivityDeletedReceived: function(scope, message) {
                var sender = message &amp;&amp; message.Header.Sender;
                // make sure the message received is the one you sent
                if (sender === "ActivityDeleted") {
                 	 // if you sent some data with the message you can get it from the message Body
                    var MessageText = message.Body;
					var array = [];
                    var esq = Ext.create("Terrasoft.EntitySchemaQuery", {
                    rootSchemaName: "Activity"
                    });
                    // Add column with account name that refers to given account.
                    esq.addColumn("Id", "Id");
                    esq.addColumn("Account.Id", "AccountId");
 
                  	esq.filters.logicalOperation = Terrasoft.LogicalOperatorType.AND;
                  	var esqAccountFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Account.Id", MessageText);
                  	var esqRdvFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "ActivityCategory.Id", "42c74c49-58e6-df11-971b-001d60e938c6");
					var esqRealiseFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Status.Id", "4bdbb88f-58e6-df11-971b-001d60e938c6");
 
 
                  	esq.filters.add("esqAccountFilter", esqAccountFilter);
                  	esq.filters.add("esqRdvFilter", esqRdvFilter);
					esq.filters.add("esqRealiseFilter", esqRealiseFilter);
                    // Get entire record collection
                    esq.getEntityCollection(function (result) {
                        if (!result.success) {
                            // error processing/logging, for example
                            this.showInformationDialog("Data query error");
                            return;
                        }
                        result.collection.each(function (item) {
                           array.push(item.get("AccountId"));
                        });
                      	if(array.length === 0)
                        {
							this.set("ContactClientOuRepresentant", {value:"f550b45d-093e-43ba-bdd1-bc0bd43c8e16" , displayValue:"Non"});
							this.save({isSilent:true});
                        }
                    }, this);
				}
            },

Regards,

 

Arthur

Hello Arthur,

 

And which connected records does the system show you? Also what happens when you drop the select result to null?

 

Best regards,

Oscar

Oscar Dylan,

 

When the screen of the connected records pop-up and I click to check the records there is nothing.

 

Also, when I set the result to null the same thing happen.

 

Regards,

 

Arthur

Arthur Hertz,

 

What is the result of the 

 

select top 5 * from MultiDeleteQueue

order by CreatedOn desc

 

right after trying to delete a record (message column values needed)? Also what error message do you receive in the application logs?

 

Best regards,

Oscar

Oscar Dylan,

 

I've put the csv file of the request in the post and also in the application logs in the "MultiDelete.log" file it's telling me this :

 

Terrasoft.Common.DbOperationException: L'instruction DELETE est en conflit avec la contrainte SAME TABLE REFERENCE "FKPkYRMonMU4O22bg1UtAWBnc3Y8". Le conflit s'est produit dans la base de données "MetropoleGestion", table "dbo.Activity", column 'ActivityConnectionId'.

 

File link : https://linkintouch-my.sharepoint.com/:x:/g/personal/ahertz_linkintouch_fr/ETEWcqG_sjxBtWFBLG7w0N8B5kXRMSIcl8gmZNvtBY-UKw?e=GhYepw

 

Regards,

 

Arthur

Arthur Hertz,

 

And can you please perform this select:

 

select ActivityConnectionId from Activity where Id = 'Id of the activity you delete'

 

and

 

select Id from Activity where ActivityConnectionId = 'Id of the activity you delete'

 

?

 

Seems that this column is not empty for some activity and uses its value as a reference for the activity you delete. 

 

Best regards,

Oscar 

Oscar Dylan,

 

 

The first request ActivityConnectionId is equal to NULL and for the second one there are no records.

 

Regards,

 

Arthur

Arthur Hertz,

 

Then you need to connect your local app to the IDE and debug the execution of deletion in the Visual Studio. There is something with the delete that is provoked by the code you've developed and you need to debug this logic.

 

Best regards,

Oscar

Oscar Dylan,

 

I've done it differently, when deleting the activity I send a message with the accountId linked to the activity deleted, and I catch it in the account edit page to do the necessaries processing. I had no problem with this method. Here is the code I've made for the sake of it.

onActivityDeletedReceived: function(scope, message) {
                var sender = message &amp;&amp; message.Header.Sender;
                // make sure the message received is the one you sent
                if (sender === "ActivityDeleted") {
                 	 // if you sent some data with the message you can get it from the message Body
                    var MessageText = message.Body;
					var array = [];
                    var esq = Ext.create("Terrasoft.EntitySchemaQuery", {
                    rootSchemaName: "Activity"
                    });
                    // Add column with account name that refers to given account.
                    esq.addColumn("Id", "Id");
                    esq.addColumn("Account.Id", "AccountId");
 
                  	esq.filters.logicalOperation = Terrasoft.LogicalOperatorType.AND;
                  	var esqAccountFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Account.Id", MessageText);
                  	var esqRdvFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "ActivityCategory.Id", "42c74c49-58e6-df11-971b-001d60e938c6");
					var esqRealiseFilter = esq.createColumnFilterWithParameter(Terrasoft.ComparisonType.EQUAL, "Status.Id", "4bdbb88f-58e6-df11-971b-001d60e938c6");
 
 
                  	esq.filters.add("esqAccountFilter", esqAccountFilter);
                  	esq.filters.add("esqRdvFilter", esqRdvFilter);
					esq.filters.add("esqRealiseFilter", esqRealiseFilter);
                    // Get entire record collection
                    esq.getEntityCollection(function (result) {
                        if (!result.success) {
                            // error processing/logging, for example
                            this.showInformationDialog("Data query error");
                            return;
                        }
                        result.collection.each(function (item) {
                           array.push(item.get("AccountId"));
                        });
                      	if(array.length === 0)
                        {
							this.set("ContactClientOuRepresentant", {value:"f550b45d-093e-43ba-bdd1-bc0bd43c8e16" , displayValue:"Non"});
							this.save({isSilent:true});
                        }
                    }, this);
				}
            },

Regards,

 

Arthur

Show all comments