This looks great, thanks for sharing! But do I understand correctly that that entire code is loaded with every page and that that code will perform multiple api calls every time? (I’m sorry if this is a very dumb question. I don’t know any javascript, just guessing.)
The code piggybacks on the existing code to load the user cards/profiles, so no additional API calls are done, just the usual one to /u/<username>.json
. But yes, the entire code is loaded on every ‘real’ page load (i.e. when you hit Discourse from an external site or from typing in a url, or refresh a page), much the same way all the rest of Discourse’s client side code is loaded on every real page load.
Is there an easy way to implement this? I would like to use external_id in my link, but I’m still not clear on how I would go about doing that.
Thanks!
This needs to be done on SSO side, so you will need to look into how your SSO is set-up.
I’m just using the WP Discourse plugin.
When I visit the user profile as admin (/admin/users/2/[username]), I do see the External ID under the Single Sign On section at the bottom.
Does that move me any further ahead in the process? Is it just a matter of properly modifying OP’s code?
@simon, is there a good way to do this in the WP Discourse plugin?
Yes, there is. What data do you want to add to the field?
Just the External ID to a custom field.
Aside from that, it would be cool if there was an easy way to do it for other fields as well. (ie location or any custom fields on the WP side).
It’s not as easy as I thought. I might not be doing this correctly.
It’s possible to set the value of a UserCustomField
through the SSO parameters sent from WordPress by hooking into the wpdc_sso_params
filter. If you create a ‘wordpress id’ User Field on Discourse, you can then create new Discourse UserCustomField
record by doing something like this:
add_filter( 'wpdc_sso_params', 'my_namespace_custom_fields', 10, 2 );
function my_namespace_custom_fields( $sso_params, $user ) {
$sso_params['custom.wordpress_id'] = $user->ID;
return $sso_params;
}
The problem I’m having is that I can’t figure out how to access the value of that record on the front-end of Discourse.
Thanks Simon! Yeah I just poked around as well and couldn’t find the field name anymore. How did you find it through the console?
My solution seems wrong. I’ll look at this some more when I get a chance.
Edit:
I was having some trouble understanding why this works, but after looking through the code a bit more this seems to make sense as a way of setting custom fields through SSO.
Create a user field on Discourse in the way outlined in the OP and then go to your profile as an admin and add a value (any value) to it. You can then go to the Discourse rails console and enter:
UserCustomField.all
A list of all the user_custom_fields on your site will be returned. It will be made up of one or more entries that look something like this:
#<UserCustomField:0x007fa02bb39d18 id: 18, user_id: 1, name: "user_field_8", value: "test value", created_at: Wed, 07 Jun 2017 01:48:10 UTC +00:00, updated_at: Wed, 07 Jun 2017 01:48:10 UTC +00:00>]
Look for the entry that has a value
attribute that matches the value you just saved in your custom field. Copy the name of that field into a function on your WordPress site that is something like this:
add_filter( 'wpdc_sso_params', 'my_namespace_set_discourse_custom_field', 10, 2 );
function my_namespace_set_discourse_custom_field( $sso_params, $user ) {
$sso_params['custom.user_field_7'] = $user->ID;
return $sso_params;
}
To use the code in the OP, replace the name value (‘User Profile’) in this line:
const externalUserIdField = siteUserFields.filterBy('name', 'User Profile')[0]
with whatever you have called the field you added on Discourse. This is the part of the code that I wasn’t understanding, but it makes more sense after looking at this: https://github.com/discourse/discourse/blob/master/app/controllers/users_controller.rb#L99
Unless there is a better way to do this, I’ll add it to the WP Discourse Plugin Tips and Tricks topic.
3 posts were split to a new topic: How to update user Web Site field via API
This guide is now updated to deprecate api.container.lookupFactory
in favor of api.modifyClass
.
I want to do something like this but then dont the users on your website now have 2 user profiles, one from discourse and one from your site?
Same here, I want to link to the external profile from the users profile/card. I have the external_id synchronised during sso, so how to create that link or rather: how do I get the external_id available as a user field as described in the first post?
For anyone who is not a coder wanting to link words in a customized user field to a webpage, here is how you do it.
I wanted to add this customized field at sign up, so I filled in the form like so:
With this code in the field description (thanks to @dax) for the linked words:
I am cool with the guidelines <a href=https://forums.wethepeoplejournal.com/faq">found here</a>
This is the custom field new members see. They click on “found here” to review our groundrules, which are strict due to the toxic climate in local town forums, which we are working to avoid:
Awesome, thanks a lot. You can even shorten the ÙRL being a relative one if you just want to link to the FAQ or ToS on the same host. That makes the string shorter and more reliable if you ever change the VHost. If you prefer to open them in a new tab, add target="_blank"
after the href.
I've read the <a href="/faq">FAQ</a> and <a href="/tos">ToS</a>.
Thanks, @dnsmichi. The shorter url and blank target edit worked like a charm.
So instead of waiting for the external user ID become available I implemented as described in the first post. Replaced the constants with my data and created a rewrite from the Discourse user ID to my main sites user ID.
It’s not working though. Only when I manually put the user id into the field of a profile it works.
Wasn’t the point not to have the need to manually put the user ID into this field as per the inactive option “Editable after signup?” What am I missing?
@techAPJ, I’m on Discourse 2.0.0b10, I’ve tried a bunch of modifications but can’t get the custom field to blend in correctly. With the default CSS it just shifts other custom fields. Any thoughts?
Also, I usually have the “Website” custom field showing after the Farm/Company…" field, any way to do that?