GLib.Notification fails to activate action with a non-null VariantType - gtk

I'm trying to send a GLib.Notification from my application and pass a string parameter.
The name of the action is action-show-chat-view, and it is registered in the activate () method of my main application class:
public class MyApplication : Gtk.Application {
protected override void activate () {
// ...
var show_chat_view_action = new GLib.SimpleAction ("action-show-chat-view", GLib.VariantType.STRING);
show_chat_view_action.activate.connect ((parameter) => {
debug ("beep boop");
debug (parameter.get_string ());
});
add_action (show_chat_view_action);
// ...
}
}
To send the notification, I do the following:
var notification = new GLib.Notification ("Hello, world");
var target = new GLib.Variant.string ("foobar");
notification.set_default_action_and_target_value ("app.action-show-chat-view", target);
app.send_notification (null, notification); // app is the instance of the MyApplication class above
The notification is sent correctly and appears as expected, however when the notification is clicked to activate the action, I receive the following error:
GLib-GIO-CRITICAL **: 13:04:37.169: g_simple_action_activate: assertion 'simple->parameter_type == NULL ? parameter == NULL : (parameter != NULL && g_variant_is_of_type (parameter, simple->parameter_type))' failed
Other things that I've tried:
If I replace GLib.VariantType.STRING with null, and pass null as the target value on the notification (and removing parameter.get_string ()), I see the "beep boop" console output so I know that everything is at least wired up correctly and calling the right methods.
I have also tried registering the action with the app. prefix as well, however I read somewhere in documentation that when added via the Application.add_action () this is implicit.
I tried creating an action group with the type string s but got the same error.
I've tried using other Variant types besides STRING
I tried adding the following check before sending the notification to see if the types align, and they did: app.get_action_parameter_type ("action-show-chat-view").equal (target.get_type ()). This failed if I used the app. prefix, however I think that's expected behavior since it's registered without the prefix?
I looked into Flatpak sandbox permissions (this part is all new to me), but since the notification is sent successfully, I don't think that's the problem.

This appears to have been a bug with xdg-desktop-portal-gtk: https://github.com/flatpak/xdg-desktop-portal-gtk/pull/359. Despite being fixed, it has not yet been included in a release.
Some related discussion on an issue logged with elementary/notifications: https://github.com/elementary/notifications/issues/153

Related

Get newly created id of a record before redirecting page

I would like to retrieve the id of a newly created record using javascript when I click on save button and just before redirecting page.
Do you have any idea please ?
Thank you !
One way to do this in Sugar 7 would be by overriding the CreateView.
Here an example of a CustomCreateView that outputs the new id in an alert-message after a new Account was successfully created, but before Sugar gets to react to the created record.
custom/modules/Accounts/clients/base/views/create/create.js:
({
extendsFrom: 'CreateView',
// This initialize function override does nothing except log to console,
// so that you can see that your custom view has been loaded.
// You can remove this function entirely. Sugar will default to CreateView's initialize then.
initialize: function(options) {
this._super('initialize', [options]);
console.log('Custom create view initialized.');
},
// saveModel is the function used to save the new record, let's override it.
// Parameters 'success' and 'error' are functions/callbacks.
// (based on clients/base/views/create/create.js)
saveModel: function(success, error) {
// Let's inject our own code into the success callback.
var custom_success = function() {
// Execute our custom code and forward all callback arguments, in case you want to use them.
this.customCodeOnCreate(arguments)
// Execute the original callback (which will show the message and redirect etc.)
success(arguments);
};
// Make sure that the "this" variable will be set to _this_ view when our custom function is called via callback.
custom_success = _.bind(custom_success , this);
// Let's call the original saveModel with our custom callback.
this._super('saveModel', [custom_success, error]);
},
// our custom code
customCodeOnCreate: function() {
console.log('customCodeOnCreate() called with these arguments:', arguments);
// Retrieve the id of the model.
var new_id = this.model.get('id');
// do something with id
if (!_.isEmpty(new_id)) {
alert('new id: ' + new_id);
}
}
})
I tested this with the Accounts module of Sugar 7.7.2.1, but it should be possible to implement this for all other sidecar modules within Sugar.
However, this will not work for modules in backward-compatibility mode (those with #bwc in their URL).
Note: If the module in question already has its own Base<ModuleName>CreateView, you probably should extend from <ModuleName>CreateView (no Base) instead of from the default CreateView.
Be aware that this code has a small chance of breaking during Sugar upgrades, e.g. if the default CreateView code receives changes in the saveModel function definition.
Also, if you want to do some further reading on extending views, there is an SugarCRM dev blog post about this topic: https://developer.sugarcrm.com/2014/05/28/extending-view-javascript-in-sugarcrm-7/
I resolved this by using logic hook (after save), for your information, I am using Sugar 6.5 no matter the version of suitecrm.
Thank you !

Dynamics CRM - Unit Testing a plugin with RhinoMocks give weird result

I am writing a unit test for a plugin using Dynamics CRM with RhinoMocks.
After stubbing out the OrganizationService.Retrieve() method, when I invoke the stubbed out method, I am getting null back.
From what I can see (correct me if I'm wrong), is that the stubbed out method signature must the same as the invocation signature.
Here is my code:
TestSetup
var someGuid = Guid.Empty;
var organisationServiceMock = MockRepository.GenerateMock<IOrganizationService>();
organisationServiceMock.Expect(x => x.Retrieve("someCrmEntity", someGuid, SomeCrmEntityColumnSetQuery.ColumnSet))
.Return(new Entity
{
LogicalName = "someCrmEntity",
Id = Guid.NewGuid(),
});
SomeCrmEntityColumnSetQuery Code
public static class SomeCrmEntityColumnSetQuery
{
public static ColumnSet ColumnSet => new ColumnSet("column1", "column2");
}
Invocation Code
var someEntity = organisationServiceMock.Retrieve("someCrmEntity", someGuid, SomeCrmEntityColumnSetQuery.ColumnSet);
//someEntity is null
Things I have tried
Removed the ColumnSet and replaced it with null - this works
Replaced the static class SomeCrmEntityColumnSetQuery with a default instance (new ColumnSet())
I have set the someGuid to Guid.Empty thinking that it was not "joining" on the correct Guid hence the null return value.
I have tried to replace .Expect() with .Stub() - no joy
Edit
In the expectation, I have tried the .WhenCalled(...) and that is how I found out that if I replace the columnSet argument with a null in the expectation and the invocation, it works. So it's go to do with something in my static class that represents a ColumnSet. The code works as I have it running in my DEV environment.
If anyone can share some light on this, that would be magic!
Charles
So I found the answer after watching a PluralSight video on RhinoMocks.
My problem was that when setting up the stub, the stub does not take values but rather the signature of the method that you are stubbing out. For e.g:
var organisationServiceMock = MockRepository.GenerateMock();
//Wrong
organisationServiceMock.Expect(x => x.Retrieve("someCrmEntity", someGuid, SomeCrmEntityColumnSetQuery.ColumnSet)).Return(new Entity());
//The stub does not care about what values are being sent into the method when invoked but rather if the method signature types match.
//Correct
organisationServiceMock.Expect(x => x.Retrieve(Arg.Is.Anything, Arg.Is.Anything, Arg.Is.Anything)).Return(new Entity());
//During the invocation, stubbed method now expects the first argument to be a string, then 2nd to be a Guid, 3rd to be a ColumnSet.
I hope this helps anyone who has also been struggling with this. :)

Calling method from console: "No current object"

I have a method that I need to test. I would like to do so from the console. Here is the method, as well as some metadata from the class:
Include HS.Common
Class Custom.class Extends Ens.BusinessOperation
{
Parameter ADAPTER = "EnsLib.EMail.OutboundAdapter";
Property Adapter As EnsLib.EMail.OutboundAdapter;
Method SendMessage(pSubject As %String, pMessage As %String, pEmailAddresses) As %Status
{
set tSC=$$$OK
set tMailMessage=##class(%Net.MailMessage).%New()
do tMailMessage.To.Insert($PIECE(pEmailAddresses,",",1))
for tI=2:1:$LENGTH(pEmailAddresses,",") {
do tMailMessage.Cc.Insert($PIECE(pEmailAddresses,",",tI))
}
set tMailMessage.Subject=pSubject
set tMailMessage.Charset="iso-8859-1"
set tSC=tMailMessage.TextData.Write(pMessage)
quit:'tSC
Set tSC1=..Adapter.SendMail(tMailMessage)
if 'tSC1 {
//Log warning about being unable to send mail.
do $SYSTEM.Status.DecomposeStatus(tSC1,.err)
$$$LOGWARNING("Could not send email: "_err(err))
kill err
}
quit tSC
}
...other methods here...
}
but when I perform this command:
set tResult = ##class(Custom.class).SendMessage("Test Subject","Test Message","my#email.com")
I get this error:
Set tSC1=..Adapter.SendMail(tMailMessage)
^
<NO CURRENT OBJECT>zSendMessage+11^Custom.class.1
I tried instantiating adapter, much like the property definition, before calling the method but that did not work. How can I call this method from a console session?
this method is an instance method, and you can't call it directly just for some class. Before, you should create an object, and then for that object, you can call any instance methods. But you still trying to call Ensemble classes, it is not so easy, because you should prepare environment, such as configured and started Ensemble Production, your class should be added as an Operation, configured and activated.
set oper=##class(Custom.class).%New("configName")
where configName - name for that operation in your production, by default it is same as class name (e.g. "Custom.class"). And now you can call your method.
write oper.SendMessage("testSubj","test body","my#mail.com")
But I would not recommend such way. It would be better if you test it through production, just sent test messages to this operation.

Debugging with monodevelop and unity crash at start

So I'm trying to start debuging with monodevelop and unity. If I understand right first step is to open monodevelop with class u want to debug and hit Run->Run with->Unity debuger. However when i do so, I get 2 errors and it doesn't work. The errors are somehow connected to Debug console class. They are:
Error CS0188: The 'this' object cannot be used before all of its fields are assigned to (CS0188) (Assembly-CSharp-firstpass)
Error CS0843: Backing field for automatically implemented property 'DebugConsole.Message.color' must be fully assigned before control is returned to the caller. Consider calling the default constructor from a constructor initializer. (CS0843) (Assembly-CSharp-firstpass)
These happens in that constructor of DebugConsole class:
public Message(object messageObject, MessageType messageType, Color displayColor) {
this.text = messageObject == null ? "<null>" : messageObject.ToString();
this.formatted = string.Empty;
this.type = messageType;
this.color = displayColor;
}
First error is in last line and second in first line of constructor.
What can i do?
Btw. when i run from unity it works fine, no errors.

Yii RBAC make Users update profile by himself

I'm trying to do this with mongodbauthmanager. I'm follow step by step in Usage section but finally i'm getting PHP warning: Illegal offset type. I had posted this question at Yii Extension before clone to SO:
Please tell me what is wrong?
1// Config
'authManager'=>array(
'class' =>'CMongoDbAuthManager',
'showErrors' => true,
),
2// Create auth items in db
$auth = new CMongoDbAuthManager();
$bizRule = 'return Yii::app()->user->id==$params["User"]->_id;';
$auth->createTask('updateSelf', 'update own information', $bizRule);
//I had tried with $auth->createOperation() but they has the same error
$role = $auth->createRole('user');
$role->addChild('updateSelf');
$auth->save();
and here is result in db
result in db http://i.minus.com/iIpXoBlDxaEfo.png
**3// Checking access in controller ** - UPDATE CODE AND ERROR
public function actionUpdate($id)
{
$model=$this->loadModel($id);
$params = array('User'=>$model);
if (!Yii::app()->user->checkAccess('updateSelf', Yii::app()->user->id,$params) )
{
throw new CHttpException(403, 'You are not authorized to perform this action');
}
//another statement ...
}
4// Getting error:
Fatal error : Cannot use object of type MongoId as array in F:\Data\03. Lab\www\yii\framework\web\auth\CAuthManager.php(150) : eval()'d code on line 1
RESOLVED PROBLEM
Base-on the answer of #Willem Renzema, I resolve my problem. Now, I update here and hope it useful for someone have this error.
0// First, config authManager with defaultRoles
'authManager'=>array(
'class'=>'CMongoDbAuthManager',
'showErrors' => true,
'defaultRoles'=> array('user'),//important, this line help we don't need assign role for every user manually
),
1// Fix save id in UserIdentity class
class UserIdentity extends CUserIdentity
{
private $_id;
//...
public function authenticate()
{
//...
$this->_id = (string)$user->_id;//force $this save _id by string, not MongoId object
//...
}
//...
}
2// Fix $bizrule in authe items
($bizrule will run by eval() in checkAccess)
//use _id as string, not MongoId object
$bizRule = 'return Yii::app()->user->id==(string)$params["User"]->_id;';
3// And user checkAccess to authorization
public function actionUpdate($id){
/**
* #var User $model
*/
$model=$this->loadModel($id);
$params = array('User'=>$model);
if (!Yii::app()->user->checkAccess('updateSelf', $params) )
{
throw new CHttpException(403, 'You are not authorized to perform this action');
}
//...
}
4// Done, now we can use checkAccess :D
First off, your original use of checkAccess was correct. Using Yii::app()->user->checkAccess() you are using the following definition:
http://www.yiiframework.com/doc/api/1.1/CWebUser#checkAccess-detail
Now, CWebUser's implementation of checkAccess calls CPHPAuthManager's implementation, which is where you encountered your problem with an illegal offset type.
http://www.yiiframework.com/doc/api/1.1/CPhpAuthManager#checkAccess-detail
An Illegal offset type means you are attempting to access an array element by specifying its key (also known as: offset) with a value that doesn't work as a key. This could be another array, an object, null, or possibly something else.
Your stack trace posted on the extensions page reveals that the following line gives the problem:
if(isset($this->_assignments[$userId][$itemName]))
So we have two possibilities for the illegal offset: $userId and $itemName.
Since $itemName is clearly a string, the problem must be with $userId.
(As a side note, the fact that your stack trace revealed surrounding code of this error also revealed that, at least for CPHPAuthManager, you are using a version of Yii that is prior to 1.1.11. Observe that lines 73 and 74 of https://github.com/yiisoft/yii/blob/1.1.11/framework/web/auth/CPhpAuthManager.php do not exist in your file's code.)
At this point I would have guessed that the problem is that the specified user is not logged in, and so Yii::app()->user->id is returning null. However, the new error you encountered when placing Yii::app()->user->id as the 2nd parameter of checkAccess reveals something else.
Since the 2nd parameter is in fact what should be the $params array that appears in your bizRule. Based on the error message, this means that Yii::app()->user->id is returning a mondoId type object.
I was unfamiliar with this type of object, so looked it up:
http://php.net/manual/en/class.mongoid.php
Long story short, you need to force Yii::app()->user->id to return the string value equivalent of this mondoId object. This likely set in your UserIdentity class in the components folder. To force it to be a string, simply place (string) to force a type conversion.
Example:
$this->_id = (string)$User->_id;
Your exact code will vary, based on what is in your UserIdentity class.
Then, restore your checkAccess to the signature you had before, and it should eliminate the Illegal offset error you encountered originally.
Note however that I have not used this extension, and while performing the following actions should fix this issue, it may cause new issues if the extension relies on the fact that Yii::app()->user->id is a mondoId object, and not a string.