Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -290,7 +290,7 @@ private boolean hasFullEntry(JsonValue entry, QuerySide querySide) {

if (entry != null) {

short ignoreFields = 0;
int ignoreFields = 0;
if (entry.isDefined("_id")) {
ignoreFields++;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2015-2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
Expand Down Expand Up @@ -47,8 +48,8 @@ define([
title = "";

this.data = {
star: "★",
hollowStar: "☆",
star: "",
hollowStar: "",
situation: args.situation,
edit: args.edit,
defaultAction: false,
Expand Down Expand Up @@ -119,12 +120,12 @@ define([
// Set viable options stars
_.each(this.model.basePolicy.options, function(action) {
tempSelector = $("#defaultActionPane select option[value='"+action+"']");
tempSelector.html(tempSelector.text() + " " + this.data.hollowStar);
tempSelector.text(tempSelector.text() + " " + this.data.hollowStar);
}, this);

// Set default option star
tempSelector = $("#defaultActionPane select option[value='"+this.model.basePolicy.action+"']");
tempSelector.html(tempSelector.text() + " " + this.data.star);
tempSelector.text(tempSelector.text() + " " + this.data.star);

this.$el.find("#defaultActionPane select").val(this.model.basePolicy.action);

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2015-2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
Expand Down Expand Up @@ -152,20 +153,24 @@ define([
tempValue,
displayValue;

// Options are built through the DOM API, never by string concatenation: the names come
// from the stored condition and must be treated as text, not markup.
_.each(this.model.sourceProps, function(source) {
if(source !== undefined) {
baseElement.append('<option value="/object/' +source +'">' +source +'</option>');
baseElement.append($("<option>").attr("value", "/object/" + source).text(source));
}
});

this.$el.find(".name").each(function(name, index){
tempValue = $(this).val();
appendElement = baseElement.clone();

if(tempValue.length > 0 && appendElement.find("option[value='/object/" +tempValue +"']").length === 0 && appendElement.find("option[value='" +tempValue +"']").length === 0) {
if(tempValue.length > 0 && appendElement.find("option").filter(function() {
return this.value === tempValue || this.value === "/object/" + tempValue;
}).length === 0) {
displayValue = tempValue.replace("/object/", "");

appendElement.append('<option value="' +tempValue +'">' +displayValue +'</option>');
appendElement.append($("<option>").attr("value", tempValue).text(displayValue));
}

$(this).replaceWith(appendElement);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
Expand Down Expand Up @@ -133,21 +134,26 @@ define([
createNameDropdown: function(input) {
var baseElement = $('<select style="width:100%;" class="name form-control"></select>'),
tempValue = $(input).val(),
displayValue;
pointer;

// Options are built through the DOM API, never by string concatenation: the names come
// from the stored condition and must be treated as text, not markup.
_.each(this.model.sourceProps, function(source) {
if(source !== undefined) {
baseElement.append('<option value="/' +source +'">' +source +'</option>');
baseElement.append($("<option>").attr("value", "/" + source).text(source));
}
});

if(tempValue.length > 0 && baseElement.find("option[value='/" +tempValue +"']").length === 0 && baseElement.find("option[value='/" +tempValue +"']").length === 0) {
displayValue = tempValue.replace("/", "");
if(tempValue.length > 0) {
// the stored name is a JSON pointer ("/mail"); tolerate a bare property name too
pointer = tempValue.charAt(0) === "/" ? tempValue : "/" + tempValue;

baseElement.append('<option value="/' +tempValue +'">' +displayValue +'</option>');
}
if(baseElement.find("option").filter(function() { return this.value === pointer; }).length === 0) {
baseElement.append($("<option>").attr("value", pointer).text(pointer.substring(1)));
}

baseElement.val(tempValue);
baseElement.val(pointer);
}

return baseElement;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2011-2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
Expand All @@ -29,7 +30,8 @@ define([
additionalFilters = data._queryFilter || [],
getFilter = (function () {
return function (filterName, filterQuery) {
return filterName + ' sw "' + filterQuery.replace(/"/g, '\\"') + '"';
// backslash first, so a value ending in a backslash cannot escape the closing quote
return filterName + ' sw "' + filterQuery.replace(/\\/g, '\\\\').replace(/"/g, '\\"') + '"';
};
}());

Expand Down
Original file line number Diff line number Diff line change
@@ -1,5 +1,58 @@
/**
* The contents of this file are subject to the terms of the Common Development and
* Distribution License (the License). You may not use this file except in compliance with the
* License.
*
* You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
* specific language governing permission and limitations under the License.
*
* When distributing Covered Software, include this CDDL Header Notice in each file and include
* the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
* Header, with the fields enclosed by brackets [] replaced by your own identifying
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
"jquery",
"org/forgerock/openidm/ui/admin/mapping/util/LinkQualifierFilterEditor"
], function (LinkQualifierFilterEditor) {
], function ($, LinkQualifierFilterEditor) {
QUnit.module('LinkQualifierFilterEditor Tests');
});

QUnit.test("createNameDropdown treats an unknown property name as text, not HTML", function (assert) {
var editor = new LinkQualifierFilterEditor(),
hostile = '/object/x"><b>y</b>',
select;

editor.model = { sourceProps: ["userName"] };
editor.$el = $('<div><input class="name"></div>');
editor.$el.find(".name").val(hostile);

editor.createNameDropdown();
select = editor.$el.find("select.name");

assert.equal(select.length, 1, "the input is replaced by a select");
assert.equal(select.find("option").length, 3, "Link Qualifier + source prop + exactly one option for the unknown value");
assert.equal(select.find("b").length, 0, "no element is created from the value");
assert.equal(select.find("option").last().attr("value"), hostile, "option value is the raw text");
assert.equal(select.find("option").last().text(), 'x"><b>y</b>', "option label is the raw text without the /object/ prefix");
assert.equal(select.val(), hostile, "the unknown value is selected");
});

QUnit.test("createNameDropdown selects a known property without adding a duplicate option", function (assert) {
var editor = new LinkQualifierFilterEditor(),
select;

editor.model = { sourceProps: ["userName", "mail"] };
editor.$el = $('<div><input class="name"></div>');
editor.$el.find(".name").val("/object/mail");

editor.createNameDropdown();
select = editor.$el.find("select.name");

assert.equal(select.find("option").length, 3, "Link Qualifier + two source props, no extra option");
assert.equal(select.val(), "/object/mail");
});
});
Original file line number Diff line number Diff line change
@@ -1,5 +1,65 @@
/**
* The contents of this file are subject to the terms of the Common Development and
* Distribution License (the License). You may not use this file except in compliance with the
* License.
*
* You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
* specific language governing permission and limitations under the License.
*
* When distributing Covered Software, include this CDDL Header Notice in each file and include
* the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
* Header, with the fields enclosed by brackets [] replaced by your own identifying
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
"jquery",
"org/forgerock/openidm/ui/admin/role/util/UserQueryFilterEditor"
], function (UserQueryFilterEditor) {
], function ($, UserQueryFilterEditor) {
QUnit.module('UserQueryFilterEditor Tests');
});

QUnit.test("createNameDropdown treats an unknown property name as text, not HTML", function (assert) {
var editor = new UserQueryFilterEditor(),
hostile = 'x"><b>y</b>',
select;

editor.model = { sourceProps: ["userName"] };

select = editor.createNameDropdown($("<input>").val(hostile));

assert.equal(select.find("option").length, 2, "exactly one option is added for the unknown value");
assert.equal(select.find("b").length, 0, "no element is created from the value");
assert.equal(select.find("option").last().attr("value"), "/" + hostile, "option value is the raw text");
assert.equal(select.find("option").last().text(), hostile, "option label is the raw text");
assert.equal(select.val(), "/" + hostile, "the unknown value is selected");
});

QUnit.test("createNameDropdown keeps an unknown JSON-pointer name as-is and labels it without the slash", function (assert) {
var editor = new UserQueryFilterEditor(),
select;

editor.model = { sourceProps: ["userName"] };

select = editor.createNameDropdown($("<input>").val("/custom"));

assert.equal(select.find("option").length, 2);
assert.equal(select.find("option").last().attr("value"), "/custom");
assert.equal(select.find("option").last().text(), "custom");
assert.equal(select.val(), "/custom");
});

QUnit.test("createNameDropdown selects a known property without adding a duplicate option", function (assert) {
var editor = new UserQueryFilterEditor(),
select;

editor.model = { sourceProps: ["userName", "mail"] };

select = editor.createNameDropdown($("<input>").val("/mail"));

assert.equal(select.find("option").length, 2, "no extra option is added");
assert.equal(select.val(), "/mail");
});
});
Original file line number Diff line number Diff line change
@@ -1,5 +1,43 @@
/**
* The contents of this file are subject to the terms of the Common Development and
* Distribution License (the License). You may not use this file except in compliance with the
* License.
*
* You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the
* specific language governing permission and limitations under the License.
*
* When distributing Covered Software, include this CDDL Header Notice in each file and include
* the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL
* Header, with the fields enclosed by brackets [] replaced by your own identifying
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
"org/forgerock/openidm/ui/admin/util/BackgridUtils"
], function (BackgridUtils) {
QUnit.module('BackgridUtils Tests');
});

function queryFilterFor(text) {
var gridState = {
state: {
filters: [{ name: "userName", query: function () { return text; } }]
}
};
return BackgridUtils.queryFilter.call(gridState, {});
}

QUnit.test("queryFilter escapes a double quote in the filter text", function (assert) {
assert.equal(queryFilterFor('a"b'), 'userName sw "a\\"b"');
});

QUnit.test("queryFilter escapes a backslash so it cannot swallow the closing quote", function (assert) {
assert.equal(queryFilterFor('a\\'), 'userName sw "a\\\\"');
});

QUnit.test("queryFilter escapes a backslash-quote sequence so it cannot break out of the literal", function (assert) {
assert.equal(queryFilterFor('a\\"b'), 'userName sw "a\\\\\\"b"');
});
});
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
* information: "Portions copyright [year] [name of copyright owner]".
*
* Copyright 2011-2016 ForgeRock AS.
* Portions Copyright 2026 3A Systems, LLC.
*/

define([
Expand Down Expand Up @@ -549,7 +550,7 @@ define([
propertyValue: el.val(),
schema: _this.data.schema,
onChange: function (value, originalPropertyValue, newText) {
_this.editor.getEditor("root" + prop.selector.replace("\\","")).setValue(JSON.stringify(value));
_this.editor.getEditor("root" + prop.selector.replace(/\\/g, "")).setValue(JSON.stringify(value));
relationshipDisplay.remove();
convertField(prop);
_this.$el.find("#resourceEditLink-" + prop.propName).text(newText);
Expand All @@ -562,7 +563,7 @@ define([
}
if ($(e.target).attr("id") === removeButtonId || $(e.target).closest(".removeRelationshipButton").attr("id") === removeButtonId) {
e.preventDefault();
_this.editor.getEditor("root" + prop.selector.replace("\\","")).setValue("null");
_this.editor.getEditor("root" + prop.selector.replace(/\\/g, "")).setValue("null");
relationshipDisplay.remove();
convertField(prop);
//_this.$el.find("#resourceEditLink-" + prop.propName).text("");
Expand All @@ -580,7 +581,7 @@ define([

convertArrayField = function(prop) {
var doConversion = function (tabView) {
_this.editor.getEditor('root' + prop.selector.replace("\\","")).destroy();
_this.editor.getEditor('root' + prop.selector.replace(/\\/g, "")).destroy();

//in case this relationship array field is returned by default
//remove it from the original version of the resource
Expand Down
Loading
Loading