Добавление параметра в URL с помощью JavaScript
в веб-приложении, которое использует вызовы AJAX, мне нужно отправить запрос, но добавить параметр в конец URL, например:
оригинальный URL:
результирующий URL:
http://server/myapp.php?id=10 & enabled=true
ищет функцию JavaScript, которая анализирует URL, глядя на каждый параметр, затем добавляет новый параметр или обновляет значение, если оно уже существует.
27 ответов:
базовая реализация, которую вам нужно будет адаптировать, будет выглядеть примерно так:
function insertParam(key, value) { key = encodeURI(key); value = encodeURI(value); var kvp = document.location.search.substr(1).split('&'); var i=kvp.length; var x; while(i--) { x = kvp[i].split('='); if (x[0]==key) { x[1] = value; kvp[i] = x.join('='); break; } } if(i<0) {kvp[kvp.length] = [key,value].join('=');} //this will reload the page, it's likely better to store this until finished document.location.search = kvp.join('&'); }это примерно в два раза быстрее, чем регулярное выражение или поисковое решение, но это полностью зависит от длины строки запроса и индекса любого соответствия
медленный метод регулярных выражений, который я сравнивал с целью завершения (приблизительно + 150% медленнее)
function insertParam2(key,value) { key = encodeURIComponent(key); value = encodeURIComponent(value); var s = document.location.search; var kvp = key+"="+value; var r = new RegExp("(&|\?)"+key+"=[^\&]*"); s = s.replace(r,""+kvp); if(!RegExp.) {s += (s.length>0 ? '&' : '?') + kvp;}; //again, do what you will here document.location.search = s; }
использование:
- https://developer.mozilla.org/en-US/docs/Web/API/URL
- https://developer.mozilla.org/fr/docs/Web/API/URLSearchParams
пример:
var url = new URL("http://foo.bar/?x=1&y=2"); // If your expected result is "http://foo.bar/?x=1&y=2&x=42" url.searchParams.append('x', 42); // If your expected result is "http://foo.bar/?x=42&y=2" url.searchParams.set('x', 42);
спасибо всем за Ваш вклад. Я использовал annakata код и изменен, чтобы также включить случай, когда в url-адресе вообще нет строки запроса. Надеюсь, это поможет.
function insertParam(key, value) { key = escape(key); value = escape(value); var kvp = document.location.search.substr(1).split('&'); if (kvp == '') { document.location.search = '?' + key + '=' + value; } else { var i = kvp.length; var x; while (i--) { x = kvp[i].split('='); if (x[0] == key) { x[1] = value; kvp[i] = x.join('='); break; } } if (i < 0) { kvp[kvp.length] = [key, value].join('='); } //this will reload the page, it's likely better to store this until finished document.location.search = kvp.join('&'); } }
Это очень простое решение. Он не контролирует существование параметра, и он не изменяет существующее значение. Он добавляет ваш параметр в конец, так что вы можете получить последнее значение в вашем внутреннем коде.
function addParameterToURL(param){ _url = location.href; _url += (_url.split('?')[1] ? '&':'?') + param; return _url; }
вот значительно упрощенная версия, делающая компромиссы для удобочитаемости и меньшего количества строк кода вместо микро-оптимизированной производительности (и мы говорим о разнице в несколько миллисекунд, реалистично... из-за характера этого (работает на месте текущего документа), это, скорее всего, будет выполняться один раз на странице).
/** * Add a URL parameter (or changing it if it already exists) * @param {search} string this is typically document.location.search * @param {key} string the key to set * @param {val} string value */ var addUrlParam = function(search, key, val){ var newParam = key + '=' + val, params = '?' + newParam; // If the "search" string exists, then build params from it if (search) { // Try to replace an existance instance params = search.replace(new RegExp('([?&])' + key + '[^&]*'), '' + newParam); // If nothing was replaced, then add the new param to the end if (params === search) { params += '&' + newParam; } } return params; };вы бы тогда использовали это так:
document.location.pathname + addUrlParam(document.location.search, 'foo', 'bar');
У меня есть "класс", который делает это, и вот он:
function QS(){ this.qs = {}; var s = location.search.replace( /^\?|#.*$/g, '' ); if( s ) { var qsParts = s.split('&'); var i, nv; for (i = 0; i < qsParts.length; i++) { nv = qsParts[i].split('='); this.qs[nv[0]] = nv[1]; } } } QS.prototype.add = function( name, value ) { if( arguments.length == 1 && arguments[0].constructor == Object ) { this.addMany( arguments[0] ); return; } this.qs[name] = value; } QS.prototype.addMany = function( newValues ) { for( nv in newValues ) { this.qs[nv] = newValues[nv]; } } QS.prototype.remove = function( name ) { if( arguments.length == 1 && arguments[0].constructor == Array ) { this.removeMany( arguments[0] ); return; } delete this.qs[name]; } QS.prototype.removeMany = function( deleteNames ) { var i; for( i = 0; i < deleteNames.length; i++ ) { delete this.qs[deleteNames[i]]; } } QS.prototype.getQueryString = function() { var nv, q = []; for( nv in this.qs ) { q[q.length] = nv+'='+this.qs[nv]; } return q.join( '&' ); } QS.prototype.toString = QS.prototype.getQueryString; //examples //instantiation var qs = new QS; alert( qs ); //add a sinle name/value qs.add( 'new', 'true' ); alert( qs ); //add multiple key/values qs.add( { x: 'X', y: 'Y' } ); alert( qs ); //remove single key qs.remove( 'new' ) alert( qs ); //remove multiple keys qs.remove( ['x', 'bogus'] ) alert( qs );Я переопределил метод toString, поэтому нет необходимости вызывать QS::getQueryString, вы можете использовать QS:: toString или, как я сделал в примерах, просто полагаться на объект, который принуждается к строке.
/** * Add a URL parameter * @param {string} url * @param {string} param the key to set * @param {string} value */ var addParam = function(url, param, value) { param = encodeURIComponent(param); var a = document.createElement('a'); param += (value ? "=" + encodeURIComponent(value) : ""); a.href = url; a.search += (a.search ? "&" : "") + param; return a.href; } /** * Add a URL parameter (or modify if already exists) * @param {string} url * @param {string} param the key to set * @param {string} value */ var addOrReplaceParam = function(url, param, value) { param = encodeURIComponent(param); var r = "([&?]|&)" + param + "\b(?:=(?:[^&#]*))*"; var a = document.createElement('a'); var regex = new RegExp(r); var str = param + (value ? "=" + encodeURIComponent(value) : ""); a.href = url; var q = a.search.replace(regex, ""+str); if (q === a.search) { a.search += (a.search ? "&" : "") + str; } else { a.search = q; } return a.href; } url = "http://www.example.com#hashme"; newurl = addParam(url, "ciao", "1"); alert(newurl);и обратите внимание, что параметры должны быть закодированы перед добавлением в строку запроса.
если у вас есть строка с url, которую вы хотите украсить с помощью param, вы можете попробовать это:
urlstring += ( urlstring.match( /[\?]/g ) ? '&' : '?' ) + 'param=value';Это означает, что ? будет префикс параметра, но если у вас уже есть ? на
urlstring, чем & будет префикс.Я бы также рекомендовал сделать
encodeURI( paramvariable )Если вы не зашит параметр, но он находится внутриparamvariable; или если у вас есть смешные персонажи в нем.посмотреть кодировка URL javascript при использовании
когда-нибудь мы увидим
?в конце URL, я нашел некоторые решения, которые генерируют результаты какfile.php?&foo=bar. я придумал свое собственное решение работать отлично, как я хочу!location.origin + location.pathname + location.search + (location.search=='' ? '?' : '&') + 'lang=ar'Примечание: расположение.происхождение не работает в IE вот его исправить.
проверить https://github.com/derek-watson/jsUri
Uri и обработка строки запроса в javascript.
этот проект включает в себя отличную библиотеку регулярных выражений parseUri Стивена Левитана. Вы можете безопасно анализировать URL-адреса всех форм и размеров, какими бы недопустимыми или отвратительными они ни были.
Это простой способ добавить параметр запроса:
const query = new URLSearchParams(window.location.search); query.append("enabled", "true");и здесь.
обратите внимание:технические характеристики.
Это то, что я использую, когда дело доходит до некоторых основных дополнений url param или обновлений на стороне сервера, как узел.js.
CoffeScript:
### @method addUrlParam Adds parameter to a given url. If the parameter already exists in the url is being replaced. @param {string} url @param {string} key Parameter's key @param {string} value Parameter's value @returns {string} new url containing the parameter ### addUrlParam = (url, key, value) -> newParam = key+"="+value result = url.replace(new RegExp('(&|\?)' + key + '=[^\&|#]*'), '' + newParam) if result is url result = if url.indexOf('?') != -1 then url.split('?')[0] + '?' + newParam + '&' + url.split('?')[1] else if url.indexOf('#') != -1 then url.split('#')[0] + '?' + newParam + '#' + url.split('#')[1] else url + '?' + newParam return resultJavaScript:
function addUrlParam(url, key, value) { var newParam = key+"="+value; var result = url.replace(new RegExp("(&|\?)"+key+"=[^\&|#]*"), '' + newParam); if (result === url) { result = (url.indexOf("?") != -1 ? url.split("?")[0]+"?"+newParam+"&"+url.split("?")[1] : (url.indexOf("#") != -1 ? url.split("#")[0]+"?"+newParam+"#"+ url.split("#")[1] : url+'?'+newParam)); } return result; } var url = "http://www.example.com?foo=bar&ciao=3&doom=5#hashme"; result1.innerHTML = addUrlParam(url, "ciao", "1");<p id="result1"></p>
следующая функция поможет вам добавлять, обновлять и удалять параметры в URL или из URL
/ / example1
var myURL = '/search'; myURL = updateUrl(myURL,'location','california'); console.log('added location...' + myURL); //added location.../search?location=california myURL = updateUrl(myURL,'location','new york'); console.log('updated location...' + myURL); //updated location.../search?location=new%20york myURL = updateUrl(myURL,'location'); console.log('removed location...' + myURL); //removed location.../search/ / example2
var myURL = '/search?category=mobile'; myURL = updateUrl(myURL,'location','california'); console.log('added location...' + myURL); //added location.../search?category=mobile&location=california myURL = updateUrl(myURL,'location','new york'); console.log('updated location...' + myURL); //updated location.../search?category=mobile&location=new%20york myURL = updateUrl(myURL,'location'); console.log('removed location...' + myURL); //removed location.../search?category=mobile/ / example3
var myURL = '/search?location=texas'; myURL = updateUrl(myURL,'location','california'); console.log('updated location...' + myURL); //added location.../search?location=california myURL = updateUrl(myURL,'location','new york'); console.log('updated location...' + myURL); //updated location.../search?location=new%20york myURL = updateUrl(myURL,'location'); console.log('removed location...' + myURL); //removed location.../search//example4
var myURL = '/search?category=mobile&location=texas'; myURL = updateUrl(myURL,'location','california'); console.log('updated location...' + myURL); //added location.../search?category=mobile&location=california myURL = updateUrl(myURL,'location','new york'); console.log('updated location...' + myURL); //updated location.../search?category=mobile&location=new%20york myURL = updateUrl(myURL,'location'); console.log('removed location...' + myURL); //removed location.../search?category=mobileздесь функция
function updateUrl(url,key,value){ if(value!=undefined){ value = encodeURI(value); } var urls = url.split('?'); var baseUrl = urls[0]; var parameters = ''; var outPara = {}; if(urls.length>1){ parameters = urls[1]; } if(parameters!=''){ parameters = parameters.split('&'); for(k in parameters){ var keyVal = parameters[k]; keyVal = keyVal.split('='); var ekey = keyVal[0]; var eval = ''; if(keyVal.length>1){ eval = keyVal[1]; } outPara[ekey] = eval; } } if(value!=undefined){ outPara[key] = value; }else{ delete outPara[key]; } parameters = []; for(var k in outPara){ parameters.push(k + '=' + outPara[k]); } var finalUrl = baseUrl; if(parameters.length>0){ finalUrl += '?' + parameters.join('&'); } return finalUrl; }
Это была моя собственная попытка, но я буду использовать ответ аннакаты, поскольку он кажется намного чище:
function AddUrlParameter(sourceUrl, parameterName, parameterValue, replaceDuplicates) { if ((sourceUrl == null) || (sourceUrl.length == 0)) sourceUrl = document.location.href; var urlParts = sourceUrl.split("?"); var newQueryString = ""; if (urlParts.length > 1) { var parameters = urlParts[1].split("&"); for (var i=0; (i < parameters.length); i++) { var parameterParts = parameters[i].split("="); if (!(replaceDuplicates && parameterParts[0] == parameterName)) { if (newQueryString == "") newQueryString = "?"; else newQueryString += "&"; newQueryString += parameterParts[0] + "=" + parameterParts[1]; } } } if (newQueryString == "") newQueryString = "?"; else newQueryString += "&"; newQueryString += parameterName + "=" + parameterValue; return urlParts[0] + newQueryString; }кроме того, я нашел этот плагин jQuery из другого сообщения на stackoverflow, и если вам нужна большая гибкость, вы можете использовать это: http://plugins.jquery.com/project/query-object
Я думаю, что код будет (не проверял):
return $.query.parse(sourceUrl).set(parameterName, parameterValue).toString();
Я бы пошел с этой небольшая, но полная библиотека для обработки URL-адресов в js:
мне нравится ответ Мехмета Фатиха Йылдыза, даже он не ответил на весь вопрос.
в той же строке, как и его ответ, я использую этот код:
" Its не контролирует существование параметра, и он не изменяет существующее значение. Он добавляет ваш параметр в конец"
/** add a parameter at the end of the URL. Manage '?'/'&', but not the existing parameters. * does escape the value (but not the key) */ function addParameterToURL(_url,_key,_value){ var param = _key+'='+escape(_value); var sep = '&'; if (_url.indexOf('?') < 0) { sep = '?'; } else { var lastChar=_url.slice(-1); if (lastChar == '&') sep=''; if (lastChar == '?') sep=''; } _url += sep + param; return _url; }и тестер:
/* function addParameterToURL_TESTER_sub(_url,key,value){ //log(_url); log(addParameterToURL(_url,key,value)); } function addParameterToURL_TESTER(){ log('-------------------'); var _url ='www.google.com'; addParameterToURL_TESTER_sub(_url,'key','value'); addParameterToURL_TESTER_sub(_url,'key','Text Value'); _url ='www.google.com?'; addParameterToURL_TESTER_sub(_url,'key','value'); _url ='www.google.com?A=B'; addParameterToURL_TESTER_sub(_url,'key','value'); _url ='www.google.com?A=B&'; addParameterToURL_TESTER_sub(_url,'key','value'); _url ='www.google.com?A=1&B=2'; addParameterToURL_TESTER_sub(_url,'key','value'); }//*/
простое решение, если у вас уже есть тег или нет, и удаляет его автоматически, поэтому он не будет продолжать добавлять равное теги, удачи
function changeURL(tag) { if(window.location.href.indexOf("?") > -1) { if(window.location.href.indexOf("&"+tag) > -1){ var url = window.location.href.replace("&"+tag,"")+"&"+tag; } else { var url = window.location.href+"&"+tag; } }else{ if(window.location.href.indexOf("?"+tag) > -1){ var url = window.location.href.replace("?"+tag,"")+"?"+tag; } else { var url = window.location.href+"?"+tag; } } window.location = url; }затем
changeURL("i=updated");
хорошо здесь я сравниваю две функции, одна из которых сделана мной (regExp), а другая - (annakata).
разделить массив:
function insertParam(key, value) { key = escape(key); value = escape(value); var kvp = document.location.search.substr(1).split('&'); var i=kvp.length; var x; while(i--) { x = kvp[i].split('='); if (x[0]==key) { x[1] = value; kvp[i] = x.join('='); break; } } if(i<0) {kvp[kvp.length] = [key,value].join('=');} //this will reload the page, it's likely better to store this until finished return "&"+kvp.join('&'); }метод регулярного выражения:
function addParameter(param, value) { var regexp = new RegExp("(\?|\&)" + param + "\=([^\&]*)(\&|$)"); if (regexp.test(document.location.search)) return (document.location.search.toString().replace(regexp, function(a, b, c, d) { return (b + param + "=" + value + d); })); else return document.location.search+ param + "=" + value; }тестирование делу:
time1=(new Date).getTime(); for (var i=0;i<10000;i++) { addParameter("test","test"); } time2=(new Date).getTime(); for (var i=0;i<10000;i++) { insertParam("test","test"); } time3=(new Date).getTime(); console.log((time2-time1)+" "+(time3-time2));кажется, что даже с самым простым решением (когда regexp используют только тест и не вводят .заменить функцию) это все еще медленнее, чем разбиение... Что ж. Регулярное выражение немного медленное, но... ух...
Если вы возитесь с URL-адресами в ссылках или где-то еще, возможно, Вам также придется учитывать хэш. Вот довольно простое для понимания решение. Вероятно, не самый быстрый так как он использует регулярное выражение... но в 99.999% случаев, разница действительно не имеет значения!
function addQueryParam( url, key, val ){ var parts = url.match(/([^?#]+)(\?[^#]*)?(\#.*)?/); var url = parts[1]; var qs = parts[2] || ''; var hash = parts[3] || ''; if ( !qs ) { return url + '?' + key + '=' + encodeURIComponent( val ) + hash; } else { var qs_parts = qs.substr(1).split("&"); var i; for (i=0;i<qs_parts.length;i++) { var qs_pair = qs_parts[i].split("="); if ( qs_pair[0] == key ){ qs_parts[ i ] = key + '=' + encodeURIComponent( val ); break; } } if ( i == qs_parts.length ){ qs_parts.push( key + '=' + encodeURIComponent( val ) ); } return url + '?' + qs_parts.join('&') + hash; } }
самое простое решение, которое я могу придумать, это этот метод, который вернет измененный URI. Я чувствую, что большинство из вас работают слишком усердно.
function setParam(uri, key, val) { return uri .replace(new RegExp("([?&]"+key+"(?=[=&#]|$)[^#&]*|(?=#|$))"), "&"+key+"="+encodeURIComponent(val)) .replace(/^([^?&]+)&/, "?"); }
насколько я могу судить, ни один из приведенных выше ответов не касается случая, когда строка запроса содержит параметры, которые сами являются массивом и, следовательно, будут появляться более одного раза, например:
http://example.com?sizes[]=a&sizes[]=bследующая функция-это то, что я написал До обновления
document.location.search. Он принимает массив массивов пар ключ / значение в качестве аргумента, и он вернет пересмотренную версию последнего, с которой вы можете делать все, что захотите. Я использую его так:var newParams = [ ['test','123'], ['best','456'], ['sizes[]','XXL'] ]; var newUrl = document.location.pathname + insertParams(newParams); history.replaceState('', '', newUrl);если текущий URL-адрес было:
http://example.com/index.php?test=replaceme&sizes[]=XLэто вам
http://example.com/index.php?test=123&sizes[]=XL&sizes[]=XXL&best=456функции
function insertParams(params) { var result; var ii = params.length; var queryString = document.location.search.substr(1); var kvps = queryString ? queryString.split('&') : []; var kvp; var skipParams = []; var i = kvps.length; while (i--) { kvp = kvps[i].split('='); if (kvp[0].slice(-2) != '[]') { var ii = params.length; while (ii--) { if (params[ii][0] == kvp[0]) { kvp[1] = params[ii][1]; kvps[i] = kvp.join('='); skipParams.push(ii); } } } } var ii = params.length; while (ii--) { if (skipParams.indexOf(ii) === -1) { kvps.push(params[ii].join('=')); } } result = kvps.length ? '?' + kvps.join('&') : ''; return result; }
попробовать
Регулярные выражения, так медленно, таким образом:var SetParamUrl = function(_k, _v) {// replace and add new parameters let arrParams = window.location.search !== '' ? decodeURIComponent(window.location.search.substr(1)).split('&').map(_v => _v.split('=')) : Array(); let index = arrParams.findIndex((_v) => _v[0] === _k); index = index !== -1 ? index : arrParams.length; _v === null ? arrParams = arrParams.filter((_v, _i) => _i != index) : arrParams[index] = [_k, _v]; let _search = encodeURIComponent(arrParams.map(_v => _v.join('=')).join('&')); let newurl = window.location.protocol + "//" + window.location.host + window.location.pathname + (arrParams.length > 0 ? '?' + _search : ''); // window.location = newurl; //reload if (history.pushState) { // without reload window.history.pushState({path:newurl}, null, newurl); } }; var GetParamUrl = function(_k) {// get parameter by key let sPageURL = decodeURIComponent(window.location.search.substr(1)), sURLVariables = sPageURL.split('&').map(_v => _v.split('=')); let _result = sURLVariables.find(_v => _v[0] === _k); return _result[1]; };пример:
// https://some.com/some_path GetParamUrl('cat');//undefined SetParamUrl('cat', "strData");// https://some.com/some_path?cat=strData GetParamUrl('cat');//strData SetParamUrl('sotr', "strDataSort");// https://some.com/some_path?cat=strData&sotr=strDataSort GetParamUrl('sotr');//strDataSort SetParamUrl('cat', "strDataTwo");// https://some.com/some_path?cat=strDataTwo&sotr=strDataSort GetParamUrl('cat');//strDataTwo //remove param SetParamUrl('cat', null);// https://some.com/some_path?sotr=strDataSort
С новыми достижениями в JS вот как можно добавить запрос param в URL:
var protocol = window.location.protocol, host = '//' + window.location.host, path = window.location.pathname, query = window.location.search; var newUrl = protocol + host + path + query + (query ? '&' : '?') + 'param=1'; window.history.pushState({path:newUrl}, '' , newUrl);также смотрите эту возможность Moziila URLSearchParams.функции append()
Это будет работать во всех современных браузерах.
function insertParam(key,value) { if (history.pushState) { var newurl = window.location.protocol + "//" + window.location.host + window.location.pathname + '?' +key+'='+value; window.history.pushState({path:newurl},'',newurl); } }
Вианней Bajart это - это правильно; однако, URL будет работать только если у вас есть полный URL-адрес с портом, хост, путь и запрос:
new URL('http://server/myapp.php?id=10&enabled=true')и URLSearchParams будет работать только если вы передадите только строку запроса:
new URLSearchParams('?id=10&enabled=true')если у вас есть неполный или относительный URL и не заботятся о базовом URL, вы можете просто разделить на
?чтобы получить строку запроса и присоединиться позже, как это:function setUrlParams(url, key, value) { url = url.split('?'); usp = new URLSearchParams(url[1]); usp.set(key, value); url[1] = usp.toString(); return url.join('?'); } let url = 'myapp.php?id=10'; url = setUrlParams(url, 'enabled', true); // url = 'myapp.php?id=10&enabled=true' url = setUrlParams(url, 'id', 11); // url = 'myapp.php?id=11&enabled=true'не совместимость с Internet Explorer.
var MyApp = new Class(); MyApp.extend({ utility: { queryStringHelper: function (url) { var originalUrl = url; var newUrl = url; var finalUrl; var insertParam = function (key, value) { key = escape(key); value = escape(value); //The previous post had the substr strat from 1 in stead of 0!!! var kvp = newUrl.substr(0).split('&'); var i = kvp.length; var x; while (i--) { x = kvp[i].split('='); if (x[0] == key) { x[1] = value; kvp[i] = x.join('='); break; } } if (i < 0) { kvp[kvp.length] = [key, value].join('='); } finalUrl = kvp.join('&'); return finalUrl; }; this.insertParameterToQueryString = insertParam; this.insertParams = function (keyValues) { for (var keyValue in keyValues[0]) { var key = keyValue; var value = keyValues[0][keyValue]; newUrl = insertParam(key, value); } return newUrl; }; return this; } } });
вот что я делаю. Используя мою функцию editParams (), вы можете добавить, удалить или изменить любой параметр, а затем использовать встроенную функцию replaceState () для обновления URL:
window.history.replaceState('object or string', 'Title', 'page.html' + editParams('enable', 'true')); // background functions below: // add/change/remove URL parameter // use a value of false to remove parameter // returns a url-style string function editParams (key, value) { key = encodeURI(key); var params = getSearchParameters(); if (Object.keys(params).length === 0) { if (value !== false) return '?' + key + '=' + encodeURI(value); else return ''; } if (value !== false) params[key] = encodeURI(value); else delete params[key]; if (Object.keys(params).length === 0) return ''; return '?' + $.map(params, function (value, key) { return key + '=' + value; }).join('&'); } // Get object/associative array of URL parameters function getSearchParameters () { var prmstr = window.location.search.substr(1); return prmstr !== null && prmstr !== "" ? transformToAssocArray(prmstr) : {}; } // convert parameters from url-style string to associative array function transformToAssocArray (prmstr) { var params = {}, prmarr = prmstr.split("&"); for (var i = 0; i < prmarr.length; i++) { var tmparr = prmarr[i].split("="); params[tmparr[0]] = tmparr[1]; } return params; }
Comments