Що повернути, якщо метод контролера Spring MVC не поверне значення?


135

Я використовую jQuery $.getJSON()для здійснення асинхронних дзвінків до мого простого Spring Spring MVC. Більшість методів регулятора Spring виглядають приблизно так:

@RequestMapping(value = "/someURL", method = RequestMethod.POST)
public @ResponseBody SomePOJO getSomeData(@ModelAttribute Widget widget,
    @RequestParam("type") String type) {
    return someDAO.getSomeData(widget, type);
}   

У мене все налаштовано так, що кожен контролер повертає @ResponseBodyяк JSON, що очікує клієнтська сторона.

Але що станеться, коли запит не повинен повертати будь-який вміст клієнтові? Можна мені:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
public @ResponseBody void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

Якщо ні, то який відповідний синтаксис тут використовувати?


Я припускаю, що якщо ви нічого не повернете, вміст не буде надісланий назад?
арахант

1
Думаю, я все-таки поверну POJO якогось типу, навіть якщо у версії 1 вашого рішення він просто вписує "успішний" булевий або щось подібне. Тоді у вас є послідовний зразок у всіх ваших методах AJAX, і то , що легше побудувати, коли виявляється, ви робите необхідність повернути що - то!
млинний будинок

На відміну від пропозицій відповіді, те, що ви спочатку мали у своєму другому фрагменті, - це прекрасно та правильний спосіб обробки POSTданих.
Бретт Райан

У цьому випадку він повернеться до нуля. @RestController публічного класу RESTControllerExample {@RequestMapping (значення = "/ службовці", метод = RequestMethod.GET) публічна недійсність getE EmployeeeNames () {EmployeeSource.getEposleees (); System.out.println ("Я закінчив"); }}
spandey

Відповіді:


256

ви можете повернути недійсні, тоді вам потрібно позначити метод за допомогою @ResponseStatus (значення = HttpStatus.OK), вам не потрібно @ResponseBody

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
@ResponseStatus(value = HttpStatus.OK)
public void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

Отримайте лише методи, що повертають 200 статус неявного коду, всі інші, що у вас є, роблять одну з трьох речей:

  • Повернення недійсним і позначте метод за допомогою @ResponseStatus(value = HttpStatus.OK)
  • Повернути об’єкт і позначити його @ResponseBody
  • Повернути HttpEntityекземпляр

2
У випадку, якщо між ними трапиться виняток із виконання, HTTP 500 буде повернуто, а не 200. Отже, якщо ваша помилка обробляється на передньому кінці, повідомлення про виняток / помилку буде відображено правильно.
Лі Чі Кіам

27
Власне, вам не потрібно встановлювати @ResponseStatusі не слід. Просто мати @ResponseBodyна voidобробці досить добре.
Бретт Райан

11
Я думаю, що буде краще повернути вміст 204 No Content замість 200 для недійсних методів
raspacorp

1
@raspacorp 200 є правильним для POST, оскільки це не означає мати тіло.
Бретт Райан

8
@BrettRyan лише як коментар, принаймні для API REST - це звичайна практика, що POST буде використовуватися для створення контенту, і в цьому випадку він зазвичай повертає ідентифікатор створеного (-і) антуа (ів), повністю створених сутностей або посилання до операції зчитування. Повернення статусу 200 без вмісту може заплутати з точки зору API REST.
raspacorp

43

Ви можете просто повернути ResponseEntity з відповідним заголовком:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
public ResponseEntity updateDataThatDoesntRequireClientToBeNotified(...){
....
return new ResponseEntity(HttpStatus.OK)
}

Якби хто-небудь зіткнувся з тією ж проблемою, що і я, це не спрацювало на старій версії весни (4.1.1), я отримав 500 помилок. Я оновив до 4.2.0, і це чудово
соус

Це мій переважний спосіб повернення порожніх 200. З весни 4.1 замість цього використовуйте шаблон конструктора: поверніть ResponseEntity.ok (). Build ();
GreenTurtle

3
Хоча, здається, ResponseEntity is a raw type. References to generic type ResponseEntity<T> should be parameterized
складено

8

Ви можете повернути об’єкт "ResponseEntity". Використання об'єкта "ResponseEntity" дуже зручно як під час побудови об'єкта відповіді (який містить тіло відгуку та код коду статусу HTTP), так і під час отримання інформації з об'єкта відповіді.

Такі методи, як getHeaders (), getBody (), getContentType (), getStatusCode () тощо, дуже легко спрощує роботу з читанням об'єкта ResponseEntity.

Вам слід використовувати об’єкт ResponseEntity з кодом статусу http 204 (Без вмісту), який спеціально визначає, що запит оброблено належним чином, а орган відповіді навмисно порожній. Використання відповідних кодів статусу для передачі потрібної інформації є дуже важливим, особливо якщо ви створюєте API, який буде використовуватися декількома клієнтськими програмами.


3
налаштування @ResponseStatus(HttpStatus.NO_CONTENT)вирішено XML Parsing Error: no root element foundдля мене в браузері
aliopi

3

Так, ви можете використовувати @ResponseBody з voidтипом повернення:

@RequestMapping(value = "/updateSomeData" method = RequestMethod.POST)
@ResponseBody
public void updateDataThatDoesntRequireClientToBeNotified(...) {
    ...
}

1
так що буде тип повернення .. це код статусу HTTP?
spandey

@techBeginner У цьому випадку 200 (ОК).
Лакатос Гюла

2

Немає нічого поганого в тому, щоб повернути порожнечу, @ResponseBodyі вам слід для POSTзапитів.

Використовуйте коди статусу HTTP, щоб визначити помилки в процедурах обробника виключень, а інші згадують статус успіху. Звичайний метод, який ви маєте, поверне код відповіді, 200якого ви хочете, будь-який обробник винятків може повернути об'єкт помилки та інший код (тобто 500).


1

Але як ваша система зростає в розмірах і функціональності ... я думаю, що повернення завжди json - це зовсім не погана ідея. Це більше питання архітектурного / "масштабного дизайну".

Можна подумати про те, щоб повернути JSON завжди з двома полями знань: кодом та даними. Якщо код - це числовий код, що вказує на успіх операції, яка повинна бути виконана, а дані - будь-які додаткові дані, пов'язані з запитуваною операцією / послугою.

Давайте, коли ми використовуємо сервера, який надає сервіс, будь-яку послугу можна перевірити, чи працює вона добре.

Тому я дотримуюся, щоб весна не керувала цим, викриваючи гібридні операції повернення (Деякі повертають дані, нічого нічого ...) .. Встановлені переконайтеся, що ваш сервер відкриває більш однорідний інтерфейс. Простіше в кінці дня.


0

Ось приклад коду, що я зробив для асинхронного методу

@RequestMapping(value = "/import", method = RequestMethod.POST)
@ResponseStatus(value = HttpStatus.OK)
public void importDataFromFile(@RequestParam("file") MultipartFile file) 
{
    accountingSystemHandler.importData(file, assignChargeCodes);
}

Вам не потрібно повертати будь-яку річ зі свого методу, все, що вам потрібно, щоб використовувати цю примітку, щоб ваш метод повинен повертатися в порядку у кожному випадку

@ResponseStatus(value = HttpStatus.OK)
Використовуючи наш веб-сайт, ви визнаєте, що прочитали та зрозуміли наші Політику щодо файлів cookie та Політику конфіденційності.
Licensed under cc by-sa 3.0 with attribution required.