ADB2C Custom policy user journey - override the content definition of each orchestration step - azure-active-directory

I have a custom policy which I am setting up which is based 2 steps in the user journey
Sign in signup unified
Self assert page.
In my RP file, I have specified ContentDefinitions for each 'type' of page so I can override these with my own. From my understanding, as the RP file is the last one point in the hierarchy, it will override always.
What I am finding is that it works for step 1, but step 2 always seems to default to the standard Microsoft page.
e.g. RP file.
<ContentDefinitions>
<!--For step 1-->
<ContentDefinition Id="api.signuporsignin">
<LoadUri>https://MYURL/custom_step1.html</LoadUri>
<RecoveryUri>~/common/default_page_error.html</RecoveryUri>
<DataUri>urn:com:microsoft:aad:b2c:elements:contract:unifiedssp:1.2.0</DataUri>
<Metadata>
<Item Key="DisplayName">Signin</Item>
</Metadata>
</ContentDefinition>
<!--For step 2-->
<ContentDefinition Id="api.selfasserted">
<LoadUri>https://MYURL/custom_step2.html</LoadUri>
<RecoveryUri>~/common/default_page_error.html</RecoveryUri>
<DataUri>urn:com:microsoft:aad:b2c:elements:contract:selfasserted:1.2.0</DataUri>
<Metadata>
<Item Key="DisplayName">Collect information from user page</Item>
</Metadata>
</ContentDefinition>
</ContentDefinitions>
Ive seen on my UserJourney that Step 1 also seems to define a ContentDefinition (a default I guess?) but specifying my own one on each step didn't seem to have any effect either.
<OrchestrationStep Order="1" Type="CombinedSignInAndSignUp" ContentDefinitionReferenceId="api.signuporsignin">
Suggestions appreciated!

Related

How to get C1 CMS username of current logged in user, not the windows user

I'm trying to filter records from a C1 CMS data folder in the Console as part of a staff profile system on my website. What I'd like to do is show a single profile record for the staff member who is logged into the C1 Console, so that they can only edit their own staff profile and nobody else's. To do this, I'd like to match up the username they logged in with with a field in the data folder for the profiles.
So far I've created the datatype BaileyWeb.University.People, some sample records, and have added tree file:
<?xml version="1.0" encoding="UTF-8"?>
<ElementStructure xmlns="http://www.composite.net/ns/management/trees/treemarkup/1.0" xmlns:f="http://www.composite.net/ns/function/1.0">
<ElementStructure.AutoAttachments>
<NamedParent Name="Content" Position="Bottom"/>
</ElementStructure.AutoAttachments>
<ElementRoot>
<Children>
<Element Label="My Profile Function" Id="MyProfileRoot" Icon="user-group">
<Children>
<DataElements Type="BaileyWeb.University.People" Label="${C1:Data:BaileyWeb.University.People:DisplayName}" Icon="user">
<Actions>
<EditDataAction Label="Edit My Profile" />
<DeleteDataAction Label="Delete My Profile" />
</Actions>
<Filters>
<FunctionFilter>
<f:function name="BaileyWeb.University.Data.MyProfile.MyFilter" xmlns:f="http://www.composite.net/ns/function/1.0" />
</FunctionFilter>
</Filters>
</DataElements>
</Children>
</Element>
</Children>
</ElementRoot>
</ElementStructure>
In my C# function, I do the filtering, as per the documentation:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Web;
namespace BaileyWeb.University.Data
{
public class MyProfile
{
public static Expression<Func<BaileyWeb.University.People, bool>> MyFilter()
{
Expression<Func<BaileyWeb.University.People, bool>> filter = f => f.UserId.Contains(System.Security.Principal.WindowsIdentity.GetCurrent().Name.ToString());
return filter;
}
}
}
Unfortunately, this doesn't work, and I'm not sure why.
I'm NOT using the Active Directory login add-on, so domain logins aren't being used here. I've tried swapping out System.Security.Principal.WindowsIdentity.GetCurrent().Name.ToString() for a simple string of "admin" (which is used as a UserID for one record in the datatype) to test it, but this also fails to return a result.
When I went back to the basic tree filtering:
<Filters>
<ParentIdFilter ParentType="BaileyWeb.University.People" ReferenceFieldName="UserId" />
<FieldFilter FieldName="UserId" FieldValue="admin"/>
</Filters>
... I got a result displayed, but this was for a static username value of "admin".
Can anyone help me solve this problem?
Did you ask for logged C1 username?
Composite.C1Console.Security.UserValidationFacade.GetUsername()

Using ADB2C phone factor technical profile to validate a phone number before creating an account

I'm trying to create a custom ADB2C policy which should follow a journey such as...
User enters a phone number to verify
User receives a code to verify the number and enters this on the view
A claim is set which is used in the next step to save to AD.
I can see I need to use the phone factor technical profile as per the Microsoft docs, but I couldn't see whether this could be done before a user has signed up as it seems to want a UserID as an input claim (see Input claims required). All the samples seem to point to MFA and editing phones already associated to a user.
Is it possible to do this?
Secondly, is there any value in mixing the one-time password technical profile in this flow or is that more for just OTP code generation (not sending and accepting the inputs from the user)?
Update
So Ive managed to create the user journey which shows the UI correctly so it seems I can enter a phone number but now when I submit it I get an error "AADB2C90154: A multi-factor verification request failed to get a session id from the service."
As far as I can tell, the session technical profile is fine so not sure what the problem could be?
I also tried disabling the session but its seems like the phone tech profile needs it?
Sample technical profile
<TechnicalProfile Id="PhoneFactor-InputOrVerify">
<DisplayName>PhoneFactor</DisplayName>
<Protocol Name="Proprietary" Handler="Web.TPEngine.Providers.PhoneFactorProtocolProvider, Web.TPEngine, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null" />
<Metadata>
<Item Key="ContentDefinitionReferenceId">api.phonefactor</Item>
<Item Key="ManualPhoneNumberEntryAllowed">true</Item>
<Item Key="setting.authenticationMode">sms</Item>
<Item Key="setting.autodial">true</Item>
</Metadata>
<CryptographicKeys>
<Key Id="issuer_secret" StorageReferenceId="B2C_1A_TokenSigningKeyContainer" />
</CryptographicKeys>
<InputClaims>
<InputClaim ClaimTypeReferenceId="userIdForMFA" PartnerClaimType="UserId" DefaultValue="TEST" />
<InputClaim ClaimTypeReferenceId="phoneNumber" />
</InputClaims>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="verifiedPhone" PartnerClaimType="Verified.OfficePhone" />
<OutputClaim ClaimTypeReferenceId="newVerifiedPhone" PartnerClaimType="newPhoneNumberEntered" />
</OutputClaims>
</TechnicalProfile>
#Raj,
I don't see how you are setting the userIdForMFA other than the default value? However, the Azure documentation isn't very clear here. Try using an inputClaimsTransformation that sets the userId Value.
For example:
Add this to the MFA technical profile:
<InputClaimsTransformations>
<InputClaimsTransformation ReferenceId="CreateUserIdForMFA2" />
</InputClaimsTransformations>
Add this to your claims transformation:
<ClaimsTransformation Id="CreateUserIdForMFA2" TransformationMethod="CreateStringClaim">
<InputParameters>
<InputParameter Id="value" DataType="string" Value="test12345#{YourTenant}.onmicrosoft.com"/>
</InputParameters>
<OutputClaims>
<OutputClaim ClaimTypeReferenceId="userIdForMFA" TransformationClaimType="createdClaim" />
</OutputClaims>
</ClaimsTransformation>

Is it possible to create an integration cartridge for BM in the Saleforce for "Marchant Tools" using controllers, not pipelines?

I must create new cartridge for integration in BM but I don't want use pipelines. Can I use the controllers for this? If yes, please provide information on how to do this.
.
Yes, you can. You need to create the bm_extensions.xml and add all the actions/entries.
Note: The file mention pipeline but It can actually be a Controller as you can see in the example I linked below.
<?xml version="1.0" encoding="ISO-8859-1" ?>
<extensions xmlns="http://www.demandware.com/xml/bmmodules/2007-12-11"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xsi:schemaLocation="http://www.demandware.com/xml/bmmodules/2007-12-11 bmext.xsd">
<menuaction id="paypal_transactions_manager" menupath="orders" position="200" site="true">
<name xml:lang="x-default">PayPal Transactions</name>
<short_description xml:lang="x-default">Manage the PayPal transactions related with this site orders.</short_description>
<description xml:lang="x-default">Manage the PayPal transactions related with this site orders.</description>
<exec pipeline="PaypalAdmin" node="Orders" />
<sub-pipelines>
<pipeline name="PaypalAdmin-Orders" />
<pipeline name="PaypalAdmin-OrderTransaction" />
<pipeline name="PaypalAdmin-Action" />
<pipeline name="PaypalAdmin-CreateNewTransaction" />
</sub-pipelines>
<icon>paypalbm/images/icon_transactions.png</icon>
</menuaction>
</extensions>
PayPal Cartridge bm_paypal is a good example to understand how is done: https://github.com/SalesforceCommerceCloud/link_paypal/tree/master/cartridges/bm_paypal/cartridge
Ps: Let me know if you cannot access the link.

Amazon MWS: getting error 99019 for XML productFeeds (SubmitFeed of type _POST_PRODUCT_DATA_)

When I try to add a product (via a SubmitFeed of type "_POST_PRODUCT_DATA_") to the Amazon Market via the Amazon MWS API I get the following error:
[Marketplace : Amazon.de] A valid value is required in either the
"quantity" or "fulfillment_center_id" field.
But there is no "quantity" or "fulfillment_center_id" field in my Product.xsd nor in the official documentation. Also the exact same feed does work without an error on my Amazon MWS sandbox account. What am I missing?
Complete XML:
<?xml version="1.0" encoding="UTF-8"?>
<AmazonEnvelope>
<Header>
<DocumentVersion>1.01</DocumentVersion>
<MerchantIdentifier>XXX</MerchantIdentifier>
</Header>
<MessageType>Product</MessageType>
<Message>
<MessageID>1</MessageID>
<OperationType>Update</OperationType>
<Product>
<SKU>123456</SKU>
<StandardProductID>
<Type>EAN</Type>
<Value>767715012826</Value>
</StandardProductID>
<ProductTaxCode>A_GEN_TAX</ProductTaxCode>
<Condition>
<ConditionType>New</ConditionType>
<ConditionNote>Zustand/condition: neu OVP</ConditionNote>
</Condition>
<DescriptionData>
<Title>Bellydance for Fitness and Fun</Title>
<Manufacturer>New World 2011</Manufacturer>
</DescriptionData>
<ProductData>
<Music>
<ProductType>
<MusicPopular>
<MediaType>audioCD</MediaType>
<NumberOfDiscs>1</NumberOfDiscs>
<Genre>New Age</Genre>
</MusicPopular>
</ProductType>
</Music>
</ProductData>
</Product>
</Message>
</AmazonEnvelope>
Make sure that you use the correct "Merchant Token" (NOT merchant id) in the tag "MerchantIdentifier" inside your feed (this isn't well documented).
<MerchantIdentifier>YOUR_MERCHANT_TOKEN</MerchantIdentifier>
You should see your Merchant Token by navigating to Sellercentral > Settings > Account Info and clicking on Your Merchant Token inside the box Business Information. If the Merchant Token isn't there (which was a common error in the past), contact the Seller Support and ask for the correct Merchant Token: Please send me my Merchant Token (NOT merchant id) for use with 3rd party software.
Try to omit additional tags describing the product, especially the whole <ProductData> section inside the <Product> element. Whenever i specified the <ProductData> section I got error 99019.
The field names in MWS error messages do not match the XML structure. I'm assuming they match the flat file (CSV) columns, but haven't actually checked.
You stated "I try to add a product", while I'm guessing that above error happened when subitting an inventory feed, which is why you won't find the anything of that sort in Product.xsd.
The corresponding XML elements are Quantity and FulfillmentCenterID, both defined in Inventory.xsd.

Spring Security 3.1 ActiveDirectoryLdapAuthenticationProvider returning partial result exception

I am trying to authenticate users to an Active Directory Instance using spring security, I am getting an Partial Results Exception. I am going around in circles trying to figure this out. Below is my config.
security-app-context
<authentication-manager erase-credentials="true">
<authentication-provider>
<user-service>
<user name="admin#damien.com" authorities="ROLE_ADMINISTRATOR" password="123admin123" />
</user-service>
</authentication-provider>
<authentication-provider ref="ldapActiveDirectoryAuthProvider"/>
</authentication-manager>
<bean id="ldapActiveDirectoryAuthProvider"
class="org.springframework.security.ldap.authentication.ad.ActiveDirectoryLdapAuthenticationProvider">
<constructor-arg value="myDomain.com" />
<constructor-arg value="ldap://ldapurl:389/" />
<property name="convertSubErrorCodesToExceptions" value="true"/>
</bean>
Error I am getting
org.springframework.dao.IncorrectResultSizeDataAccessException: Incorrect result size: expected 1, actual 0 org.springframework.security.ldap.SpringSecurityLdapTemplate.searchForSingleEntryInternal(SpringSecurityLdapTemplate.java:239)
I am struggling to find examples and the documentation indicates I am working in the right direction.
This is from the logs
SpringSecurityLdapTemplate.java 213 - Searching for entry under DN '', base = 'dc=myDomain,dc=com', filter = '(&(objectClass=user)(userPrincipalName={0}))'
and this is what I would expect that to look like on a successful attempt from some scripts that work
Searching for entry under DN 'OU=Users and Groups,DC=one,DC=two,DC=myDomain,DC=com', base = 'OU=Users and Groups,DC=one,DC=two,DC=myDomain,DC=com', filter = '(&(objectClass=user)(userPrincipalName={0}))'
Do I need to get the DN populated? How? I have looked through the ActiveDirectoryLdapAuthenticationProvider properties and don't see a way? Also the base is off but myDomain.com is the correct domain for users e.g john.doe#myDomain.com. Has anyone come across a similar problem?
To solve this I used the default LDAP provider which enables user search base to be specified, specifying the user search base and user search filter.
<ldap-authentication-provider
user-search-base="OU=Users and Groups,DC=abc,DC=myDomain,DC=com"
user-search-filter="userPrincipalName={0}" />
A user would then be logging in with john.doe#myDomain.com but the usersearch base is more specific(abc.myDomain.com). I believe AD Spring was falling down due to this.

Resources