diff --git a/core/src/main/java/jenkins/model/experimentalflags/RemovePrototypeUserExperimentalFlag.java b/core/src/main/java/jenkins/model/experimentalflags/RemovePrototypeUserExperimentalFlag.java
deleted file mode 100644
index a2773986cfda..000000000000
--- a/core/src/main/java/jenkins/model/experimentalflags/RemovePrototypeUserExperimentalFlag.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * The MIT License
- *
- * Copyright (c) 2023, CloudBees, Inc.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy
- * of this software and associated documentation files (the "Software"), to deal
- * in the Software without restriction, including without limitation the rights
- * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
- * copies of the Software, and to permit persons to whom the Software is
- * furnished to do so, subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in
- * all copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
- * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
- * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
- * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
- * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
- * THE SOFTWARE.
- */
-
-package jenkins.model.experimentalflags;
-
-import edu.umd.cs.findbugs.annotations.NonNull;
-import edu.umd.cs.findbugs.annotations.Nullable;
-import hudson.Extension;
-
-@Extension
-public final class RemovePrototypeUserExperimentalFlag extends BooleanUserExperimentalFlag {
-
- public RemovePrototypeUserExperimentalFlag() {
- super("remove-prototype.flag");
- }
-
- @NonNull
- @Override
- public Boolean getDefaultValue() {
- return false;
- }
-
- @Override
- public String getDisplayName() {
- return "Remove Prototype.js";
- }
-
- @Nullable
- @Override
- public String getShortDescription() {
- return "Remove Prototype.js from all Jenkins UI pages. This will break anything that depends on Prototype.js.";
- }
-}
diff --git a/core/src/main/resources/jenkins/security/apitoken/LegacyApiTokenAdministrativeMonitor/resources.js b/core/src/main/resources/jenkins/security/apitoken/LegacyApiTokenAdministrativeMonitor/resources.js
index dc31f9d20f4a..4387cceb1ca1 100644
--- a/core/src/main/resources/jenkins/security/apitoken/LegacyApiTokenAdministrativeMonitor/resources.js
+++ b/core/src/main/resources/jenkins/security/apitoken/LegacyApiTokenAdministrativeMonitor/resources.js
@@ -109,13 +109,9 @@ function confirmAndRevokeAllSelected(button) {
selectedValues.push({ userId: userId, uuid: uuid });
}
- // TODO simplify when Prototype.js is removed
-
fetch(url, {
method: "post",
- body: Object.toJSON
- ? Object.toJSON({ values: selectedValues })
- : JSON.stringify({ values: selectedValues }),
+ body: JSON.stringify({ values: selectedValues }),
headers: crumb.wrap({ "Content-Type": "application/json" }),
}).then(() => window.location.reload());
},
diff --git a/core/src/main/resources/lib/layout/layout.jelly b/core/src/main/resources/lib/layout/layout.jelly
index 6331d63dcbc1..877a4463356a 100644
--- a/core/src/main/resources/lib/layout/layout.jelly
+++ b/core/src/main/resources/lib/layout/layout.jelly
@@ -123,10 +123,6 @@ THE SOFTWARE.
-
-
-
-
diff --git a/test/src/test/java/hudson/ExceptionTest.java b/test/src/test/java/hudson/ExceptionTest.java
deleted file mode 100644
index f105d6d5184c..000000000000
--- a/test/src/test/java/hudson/ExceptionTest.java
+++ /dev/null
@@ -1,42 +0,0 @@
-package hudson;
-
-import hudson.model.InvisibleAction;
-import hudson.model.RootAction;
-import org.htmlunit.ScriptException;
-import org.htmlunit.WebClientUtil;
-import org.junit.Assert;
-import org.junit.Rule;
-import org.junit.Test;
-import org.jvnet.hudson.test.JenkinsRule;
-import org.jvnet.hudson.test.JenkinsRule.WebClient;
-import org.jvnet.hudson.test.TestExtension;
-
-/**
- * @author Kohsuke Kawaguchi
- */
-public class ExceptionTest {
-
- @Rule public JenkinsRule j = new JenkinsRule();
-
- /**
- * Makes sure that an AJAX handler error results in a fatal problem in the unit test.
- */
- @Test
- public void testAjaxError() throws Exception {
- WebClient webClient = j.createWebClient();
- WebClientUtil.ExceptionListener exceptionListener = WebClientUtil.addExceptionListener(webClient);
- webClient.goTo("self/ajaxError");
-
- // Check for the error.
- ScriptException e = exceptionListener.getExpectedScriptException();
- Assert.assertTrue(e.getMessage().contains("simulated error"));
- }
-
- @TestExtension
- public static final class RootActionImpl extends InvisibleAction implements RootAction {
- @Override
- public String getUrlName() {
- return "self";
- }
- }
-}
diff --git a/test/src/test/resources/hudson/ExceptionTest/RootActionImpl/ajaxError.jelly b/test/src/test/resources/hudson/ExceptionTest/RootActionImpl/ajaxError.jelly
deleted file mode 100644
index e6e48d02e1dd..000000000000
--- a/test/src/test/resources/hudson/ExceptionTest/RootActionImpl/ajaxError.jelly
+++ /dev/null
@@ -1,41 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/test/src/test/resources/lib/form/JSON.js b/test/src/test/resources/lib/form/JSON.js
index b3a66ff33f89..ec01bd2ad9fd 100644
--- a/test/src/test/resources/lib/form/JSON.js
+++ b/test/src/test/resources/lib/form/JSON.js
@@ -5,14 +5,7 @@ if (typeof JSON=="undefined") {
return String.evalJSON(str);
},
stringify : function (obj) {
- // TODO simplify when Prototype.js is removed
- if (Object.toJSON) {
- // Prototype.js
- return Object.toJSON(obj);
- } else {
- // Standard
- return JSON.stringify(obj);
- }
+ return JSON.stringify(obj);
}
};
-}
\ No newline at end of file
+}
diff --git a/war/.eslintignore b/war/.eslintignore
index 447af802bf7e..e7574ace3dd4 100644
--- a/war/.eslintignore
+++ b/war/.eslintignore
@@ -11,5 +11,4 @@ jsbundles
# External scripts
src/main/webapp/scripts/yui
-src/main/webapp/scripts/prototype.js
src/main/js/plugin-setup-wizard/bootstrap-detached.js
diff --git a/war/.prettierignore b/war/.prettierignore
index 226b72ce8e7d..8047dce8ba4f 100644
--- a/war/.prettierignore
+++ b/war/.prettierignore
@@ -12,7 +12,6 @@ node/
# libraries / external deps / generated files
src/main/js/plugin-setup-wizard/bootstrap-detached.js
src/main/webapp/scripts/yui
-src/main/webapp/scripts/prototype.js
src/main/webapp/jsbundles/
src/main/scss/_bootstrap.scss
diff --git a/war/src/main/js/util/jenkins.js b/war/src/main/js/util/jenkins.js
index ddb1464108d3..f3fede3e7096 100644
--- a/war/src/main/js/util/jenkins.js
+++ b/war/src/main/js/util/jenkins.js
@@ -17,42 +17,6 @@ jenkins.baseUrl = function () {
return u;
};
-// awful hack to get around JSONifying things with Prototype taking over wrong. ugh. Prototype is the worst.
-jenkins.stringify = function (o) {
- if (Array.prototype.toJSON) {
- // Prototype f's this up something bad
- var protoJSON = {
- a: Array.prototype.toJSON,
- o: Object.prototype.toJSON,
- h: Hash.prototype.toJSON,
- s: String.prototype.toJSON,
- };
- try {
- delete Array.prototype.toJSON;
- delete Object.prototype.toJSON;
- delete Hash.prototype.toJSON;
- delete String.prototype.toJSON;
-
- return JSON.stringify(o);
- } finally {
- if (protoJSON.a) {
- Array.prototype.toJSON = protoJSON.a;
- }
- if (protoJSON.o) {
- Object.prototype.toJSON = protoJSON.o;
- }
- if (protoJSON.h) {
- Hash.prototype.toJSON = protoJSON.h;
- }
- if (protoJSON.s) {
- String.prototype.toJSON = protoJSON.s;
- }
- }
- } else {
- return JSON.stringify(o);
- }
-};
-
/**
* redirect
*/
@@ -82,7 +46,7 @@ jenkins.get = function (url, success, options) {
};
/**
- * Jenkins AJAX POST callback, formats data as a JSON object post (note: works around prototype.js ugliness using stringify() above)
+ * Jenkins AJAX POST callback, formats data as a JSON object post
* If last parameter is an object, will be extended to jQuery options (e.g. pass { error: function() ... } to handle errors)
*/
jenkins.post = function (url, data, success, options) {
@@ -110,7 +74,7 @@ jenkins.post = function (url, data, success, options) {
formBody = $.extend({}, formBody);
formBody[crumb.fieldName] = crumb.value;
}
- formBody = jenkins.stringify(formBody);
+ formBody = JSON.stringify(formBody);
}
var args = {
diff --git a/war/src/main/webapp/scripts/hudson-behavior.js b/war/src/main/webapp/scripts/hudson-behavior.js
index e93c5cedcfc1..cd35a3cd6032 100644
--- a/war/src/main/webapp/scripts/hudson-behavior.js
+++ b/war/src/main/webapp/scripts/hudson-behavior.js
@@ -2200,6 +2200,7 @@ function encode(str) {
// when there are multiple form elements of the same name,
// this method returns the input field of the given name that pairs up
// with the specified 'base' input element.
+// eslint-disable-next-line no-unused-vars
function findMatchingFormInput(base, name) {
// find the FORM element that owns us
var f = base.closest("form");
@@ -2232,17 +2233,6 @@ function findMatchingFormInput(base, name) {
return null; // not found
}
-// TODO remove when Prototype.js is removed
-if (typeof Form === "object") {
- /** @deprecated For backward compatibility only; use {@link findMatchingFormInput} instead. */
- Form.findMatchingInput = function (base, name) {
- console.warn(
- "Deprecated call to Form.findMatchingInput detected; use findMatchingFormInput instead.",
- );
- return findMatchingFormInput(base, name);
- };
-}
-
// eslint-disable-next-line no-unused-vars
function toQueryString(params) {
var query = "";
@@ -2627,14 +2617,7 @@ function buildFormTree(form) {
}
}
- // TODO simplify when Prototype.js is removed
- if (Object.toJSON) {
- // Prototype.js
- jsonElement.value = Object.toJSON(form.formDom);
- } else {
- // Standard
- jsonElement.value = JSON.stringify(form.formDom);
- }
+ jsonElement.value = JSON.stringify(form.formDom);
// clean up
for (i = 0; i < doms.length; i++) {
@@ -2803,15 +2786,6 @@ function createComboBox(idOrField, valueFunction) {
}
}
-// Exception in code during the AJAX processing should be reported,
-// so that our users can find them more easily.
-// TODO remove when Prototype.js is removed
-if (typeof Ajax === "object" && Ajax.Request) {
- Ajax.Request.prototype.dispatchException = function (e) {
- throw e;
- };
-}
-
// event callback when layouts/visibility are updated and elements might have moved around
var layoutUpdateCallback = {
callbacks: [],
diff --git a/war/src/main/webapp/scripts/prototype.js b/war/src/main/webapp/scripts/prototype.js
deleted file mode 100644
index f93b469228b3..000000000000
--- a/war/src/main/webapp/scripts/prototype.js
+++ /dev/null
@@ -1,6133 +0,0 @@
-/* Prototype JavaScript framework, version 1.7
- * (c) 2005-2010 Sam Stephenson
- *
- * Prototype is freely distributable under the terms of an MIT-style license.
- * For details, see the Prototype web site: http://www.prototypejs.org/
- *
- *--------------------------------------------------------------------------*/
-
-var Prototype = {
-
- Version: '1.7',
-
- Browser: (function(){
- var ua = navigator.userAgent;
- var isOpera = Object.prototype.toString.call(window.opera) == '[object Opera]';
- return {
- IE: !!window.attachEvent && !isOpera,
- Opera: isOpera,
- WebKit: ua.indexOf('AppleWebKit/') > -1,
- Gecko: ua.indexOf('Gecko') > -1 && ua.indexOf('KHTML') === -1,
- MobileSafari: /Apple.*Mobile/.test(ua)
- }
- })(),
-
- BrowserFeatures: {
- XPath: !!document.evaluate,
-
- SelectorsAPI: !!document.querySelector,
-
- ElementExtensions: (function() {
- var constructor = window.Element || window.HTMLElement;
- return !!(constructor && constructor.prototype);
- })(),
- SpecificElementExtensions: (function() {
- if (typeof window.HTMLDivElement !== 'undefined')
- return true;
-
- var div = document.createElement('div'),
- form = document.createElement('form'),
- isSupported = false;
-
- if (div['__proto__'] && (div['__proto__'] !== form['__proto__'])) {
- isSupported = true;
- }
-
- div = form = null;
-
- return isSupported;
- })()
- },
-
- ScriptFragment: '