mirror of
https://github.com/emilybache/GildedRose-Refactoring-Kata.git
synced 2026-02-19 08:21:37 +00:00
updated kata
This commit is contained in:
parent
ca6a1d5ba7
commit
1f8bcf777b
@ -1,5 +1,6 @@
|
||||
plugins {
|
||||
id 'java'
|
||||
id "io.freefair.lombok" version "6.0.0-m2"
|
||||
}
|
||||
|
||||
repositories {
|
||||
@ -11,6 +12,7 @@ dependencies {
|
||||
testImplementation 'org.junit.jupiter:junit-jupiter-params:5.6.2'
|
||||
testImplementation 'org.junit.jupiter:junit-jupiter-engine:5.6.2'
|
||||
testImplementation 'com.approvaltests:approvaltests:5.0.0'
|
||||
implementation 'org.mockito:mockito-core:3.9.0'
|
||||
}
|
||||
|
||||
group = 'com.gildedrose'
|
||||
|
||||
@ -1,62 +1,24 @@
|
||||
package com.gildedrose;
|
||||
|
||||
class GildedRose {
|
||||
Item[] items;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
|
||||
public GildedRose(Item[] items) {
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class GildedRose {
|
||||
private final List<QualityItem> items;
|
||||
private final QualityItemHandler qualityItemHandler;
|
||||
|
||||
public GildedRose(List<QualityItem> items, QualityItemHandler qualityItemHandler) {
|
||||
this.items = items;
|
||||
this.qualityItemHandler = qualityItemHandler;
|
||||
}
|
||||
|
||||
public List<QualityItem> getItems() {
|
||||
return new ArrayList<>(items);
|
||||
}
|
||||
|
||||
public void updateQuality() {
|
||||
for (int i = 0; i < items.length; i++) {
|
||||
if (!items[i].name.equals("Aged Brie")
|
||||
&& !items[i].name.equals("Backstage passes to a TAFKAL80ETC concert")) {
|
||||
if (items[i].quality > 0) {
|
||||
if (!items[i].name.equals("Sulfuras, Hand of Ragnaros")) {
|
||||
items[i].quality = items[i].quality - 1;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if (items[i].quality < 50) {
|
||||
items[i].quality = items[i].quality + 1;
|
||||
|
||||
if (items[i].name.equals("Backstage passes to a TAFKAL80ETC concert")) {
|
||||
if (items[i].sellIn < 11) {
|
||||
if (items[i].quality < 50) {
|
||||
items[i].quality = items[i].quality + 1;
|
||||
}
|
||||
}
|
||||
|
||||
if (items[i].sellIn < 6) {
|
||||
if (items[i].quality < 50) {
|
||||
items[i].quality = items[i].quality + 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (!items[i].name.equals("Sulfuras, Hand of Ragnaros")) {
|
||||
items[i].sellIn = items[i].sellIn - 1;
|
||||
}
|
||||
|
||||
if (items[i].sellIn < 0) {
|
||||
if (!items[i].name.equals("Aged Brie")) {
|
||||
if (!items[i].name.equals("Backstage passes to a TAFKAL80ETC concert")) {
|
||||
if (items[i].quality > 0) {
|
||||
if (!items[i].name.equals("Sulfuras, Hand of Ragnaros")) {
|
||||
items[i].quality = items[i].quality - 1;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
items[i].quality = items[i].quality - items[i].quality;
|
||||
}
|
||||
} else {
|
||||
if (items[i].quality < 50) {
|
||||
items[i].quality = items[i].quality + 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
items.replaceAll(qualityItemHandler::processOneItem);
|
||||
}
|
||||
}
|
||||
28
Java/src/main/java/com/gildedrose/QualityItemHandler.java
Normal file
28
Java/src/main/java/com/gildedrose/QualityItemHandler.java
Normal file
@ -0,0 +1,28 @@
|
||||
package com.gildedrose;
|
||||
|
||||
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import com.gildedrose.itemtorequest.ProcessingRequestFromQualityItem;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory;
|
||||
|
||||
public class QualityItemHandler {
|
||||
private final ProcessorFactory processorFactory;
|
||||
private final ProcessingRequestFromQualityItem processingRequestFromQualityItem;
|
||||
private final QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactory;
|
||||
|
||||
QualityItemHandler(ProcessorFactory processorFactory, ProcessingRequestFromQualityItem processingRequestFromQualityItem,
|
||||
QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactory) {
|
||||
this.processorFactory = processorFactory;
|
||||
this.processingRequestFromQualityItem = processingRequestFromQualityItem;
|
||||
this.qualityItemFromProcessingResponseFactory = qualityItemFromProcessingResponseFactory;
|
||||
}
|
||||
|
||||
QualityItem processOneItem(QualityItem qualityItem) {
|
||||
return qualityItemFromProcessingResponseFactory.get(qualityItem).toQualityItem(
|
||||
qualityItem,
|
||||
processorFactory.get(qualityItem).
|
||||
processItem(processingRequestFromQualityItem.get(qualityItem))
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,12 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton;
|
||||
|
||||
import com.gildedrose.itemsorts.AgedBrie;
|
||||
|
||||
public class AgedBrieProcessor extends QualityItemProcessorSkeleton<AgedBrie> implements QualityItemProcessor<AgedBrie> {
|
||||
@Override
|
||||
int qualityFunction(int oldQuality, int qualityChange) {
|
||||
return oldQuality + qualityChange;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,28 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton;
|
||||
import com.gildedrose.itemsorts.BackstagePass;
|
||||
|
||||
public class BackstagePassProcessor extends QualityItemProcessorSkeleton<BackstagePass> implements QualityItemProcessor<BackstagePass>{
|
||||
|
||||
public static final int FIVE_DAYS_BEFORE_CONCERT = 5;
|
||||
public static final int TEN_DAYS_BEFORE_CONCERT = 10;
|
||||
|
||||
@Override
|
||||
int qualityFunction(int oldQuality, int qualityChange) {
|
||||
return oldQuality + qualityChange;
|
||||
}
|
||||
|
||||
@Override
|
||||
int calculateQualityChange(int sellIn, int oldQuality) {
|
||||
if (sellIn < 0) {
|
||||
return -oldQuality;
|
||||
} else if (sellIn < FIVE_DAYS_BEFORE_CONCERT) {
|
||||
return 3;
|
||||
} else if (sellIn < TEN_DAYS_BEFORE_CONCERT) {
|
||||
return 2;
|
||||
} else {
|
||||
return 1;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,15 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton;
|
||||
import com.gildedrose.itemsorts.ConjuredItem;
|
||||
|
||||
|
||||
public class ConjuredItemProcessor extends QualityItemProcessorSkeleton<ConjuredItem> implements QualityItemProcessor<ConjuredItem> {
|
||||
|
||||
public static final int CONJURED_ITEM_QUALITY_CHANGE_MULTIPLIER = 2;
|
||||
|
||||
@Override
|
||||
int applyQualityChangeMultiplier(int qualityChange) {
|
||||
return CONJURED_ITEM_QUALITY_CHANGE_MULTIPLIER * qualityChange;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,8 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
|
||||
|
||||
public class NormalItemProcessor extends QualityItemProcessorSkeleton<NormalItem> implements QualityItemProcessor<NormalItem> {
|
||||
}
|
||||
@ -0,0 +1,37 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Getter;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
public class ProcessorFactory {
|
||||
static final String EXCEPTION_MESSAGE_TEMPLATE = "Item processor for the item of type %s is not found. Make sure that the factory" +
|
||||
"is configured correctly";
|
||||
private final Map<Class<? extends QualityItem>, QualityItemProcessor<? extends QualityItem>> qualityItemsProcessors = new HashMap<>();
|
||||
|
||||
|
||||
public ProcessorFactory(List<ProcessorFactoryItem<?>> qualityItemProcessors) {
|
||||
qualityItemProcessors.forEach(processorFactoryItem -> qualityItemsProcessors.put(processorFactoryItem.getItemType(),processorFactoryItem.getItemProcessor()));
|
||||
}
|
||||
|
||||
@Getter
|
||||
@AllArgsConstructor
|
||||
public static class ProcessorFactoryItem<T extends QualityItem> {
|
||||
private final Class<T> itemType;
|
||||
private final QualityItemProcessor<T> itemProcessor;
|
||||
}
|
||||
|
||||
public QualityItemProcessor<QualityItem> get(QualityItem qualityItem) {
|
||||
Class<? extends QualityItem> aClass = qualityItem.getClass();
|
||||
QualityItemProcessor<? extends QualityItem> qualityItemProcessor = Optional.ofNullable(qualityItemsProcessors.get(aClass)).orElseThrow(
|
||||
() -> new IllegalArgumentException(String.format(EXCEPTION_MESSAGE_TEMPLATE, aClass)));
|
||||
@SuppressWarnings("unchecked") // unnecessary
|
||||
QualityItemProcessor<QualityItem> qualityItemProcessorCasted = (QualityItemProcessor<QualityItem>) qualityItemProcessor;
|
||||
return qualityItemProcessorCasted;
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,86 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.EqualsAndHashCode;
|
||||
import lombok.Getter;
|
||||
|
||||
|
||||
public interface QualityItemProcessor<T extends QualityItem> {
|
||||
ProcessingResponse<T> processItem(ProcessingRequest<T> processingRequest);
|
||||
|
||||
|
||||
@EqualsAndHashCode
|
||||
@Getter
|
||||
@AllArgsConstructor
|
||||
class ProcessingResponse<T extends QualityItem> {
|
||||
private final int sellIn;
|
||||
private final int quality;
|
||||
}
|
||||
|
||||
@EqualsAndHashCode
|
||||
@Getter
|
||||
@AllArgsConstructor
|
||||
class ProcessingRequest<T extends QualityItem> {
|
||||
private final int sellIn;
|
||||
private final int quality;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* A skeleton intended for subclassing
|
||||
*
|
||||
* @param <T> - type of the item
|
||||
*/
|
||||
abstract class QualityItemProcessorSkeleton<T extends QualityItem> implements QualityItemProcessor<T> {
|
||||
static final int QUALITY_CHANGE_AFTER_SELL_DATE = 2;
|
||||
static final int QUALITY_CHANGE_BEFORE_SELL_DATE = 1;
|
||||
static final int MAX_QUALITY = 50;
|
||||
static final int MIN_QUALITY = 0;
|
||||
public static final int DEFAULT_QUALITY_CHANGE_MULTIPLIER = 1;
|
||||
|
||||
|
||||
@Override
|
||||
public ProcessingResponse<T> processItem(ProcessingRequest<T> processingRequest) {
|
||||
int newSellIn = calculateNewSellIn(processingRequest.getSellIn());
|
||||
int newQuality = calculateNewQuality(newSellIn, processingRequest.getQuality());
|
||||
return new ProcessingResponse<>(newSellIn, newQuality);
|
||||
}
|
||||
|
||||
int calculateNewSellIn(int oldSellIn) {
|
||||
return oldSellIn - 1;
|
||||
}
|
||||
|
||||
int calculateNewQuality(int newSellIn, int oldQuality) {
|
||||
return qualityLimitsCheck(qualityFunction(oldQuality, applyQualityChangeMultiplier(calculateQualityChange(newSellIn, oldQuality))));
|
||||
}
|
||||
|
||||
int qualityFunction(int oldQuality, int qualityChange) {
|
||||
return oldQuality - qualityChange;
|
||||
}
|
||||
|
||||
int applyQualityChangeMultiplier(int qualityChange) {
|
||||
return DEFAULT_QUALITY_CHANGE_MULTIPLIER * qualityChange;
|
||||
}
|
||||
|
||||
int calculateQualityChange(int sellIn, int oldQuality) {
|
||||
if (sellIn < 0) {
|
||||
return QUALITY_CHANGE_AFTER_SELL_DATE;
|
||||
} else {
|
||||
return QUALITY_CHANGE_BEFORE_SELL_DATE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
int qualityLimitsCheck(int quality) {
|
||||
if (quality > MAX_QUALITY) {
|
||||
return MAX_QUALITY;
|
||||
} else if (quality < MIN_QUALITY) {
|
||||
return MIN_QUALITY;
|
||||
} else {
|
||||
return quality;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
|
||||
public class SulfurasProcessor implements QualityItemProcessor<Sulfuras> {
|
||||
@Override
|
||||
public ProcessingResponse<Sulfuras> processItem(ProcessingRequest<Sulfuras> processingRequest) {
|
||||
return new ProcessingResponse<>(processingRequest.getSellIn(), processingRequest.getQuality());
|
||||
}
|
||||
}
|
||||
10
Java/src/main/java/com/gildedrose/itemsorts/AgedBrie.java
Normal file
10
Java/src/main/java/com/gildedrose/itemsorts/AgedBrie.java
Normal file
@ -0,0 +1,10 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem.QualityItemSkeleton;
|
||||
|
||||
|
||||
public class AgedBrie extends QualityItemSkeleton {
|
||||
public AgedBrie(String name, int sellIn, int quality) {
|
||||
super(name, sellIn, quality);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,9 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem.QualityItemSkeleton;
|
||||
|
||||
public class BackstagePass extends QualityItemSkeleton {
|
||||
public BackstagePass(String name, int sellIn, int quality) {
|
||||
super(name, sellIn, quality);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,9 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem.QualityItemSkeleton;
|
||||
|
||||
public class ConjuredItem extends QualityItemSkeleton implements QualityItem {
|
||||
public ConjuredItem(String name, int sellIn, int quality) {
|
||||
super(name, sellIn, quality);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,9 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem.QualityItemSkeleton;
|
||||
|
||||
public class NormalItem extends QualityItemSkeleton implements QualityItem {
|
||||
public NormalItem(String name, int sellIn, int quality) {
|
||||
super(name, sellIn, quality);
|
||||
}
|
||||
}
|
||||
65
Java/src/main/java/com/gildedrose/itemsorts/QualityItem.java
Normal file
65
Java/src/main/java/com/gildedrose/itemsorts/QualityItem.java
Normal file
@ -0,0 +1,65 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.Item;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Getter;
|
||||
|
||||
public interface QualityItem {
|
||||
String getName();
|
||||
|
||||
int getSellIn();
|
||||
|
||||
int getQuality();
|
||||
|
||||
/**
|
||||
* Skeleton class intended for subclassing
|
||||
*/
|
||||
abstract class QualityItemSkeleton implements QualityItem {
|
||||
private final Item item;
|
||||
|
||||
public QualityItemSkeleton(String name, int sellIn, int quality) {
|
||||
this.item = new Item(name, sellIn, quality);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getName() {
|
||||
return item.name;
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return item.toString();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getQuality() {
|
||||
return item.quality;
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getSellIn() {
|
||||
return item.sellIn;
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean equals(Object other) {
|
||||
if (!(other instanceof QualityItem) || other.getClass() != this.getClass()) {
|
||||
return false;
|
||||
}
|
||||
QualityItem qualityItem = (QualityItem) other;
|
||||
return (this.getName().equals(qualityItem.getName())) &&
|
||||
(this.getQuality() == qualityItem.getQuality()) &&
|
||||
(this.getSellIn() == qualityItem.getSellIn());
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
public int hashCode() {
|
||||
int result = getName() == null ? 0 : getName().hashCode();
|
||||
result += 31 * result + getQuality();
|
||||
result += 31 * result + getSellIn();
|
||||
result += 31 * result + this.getClass().getName().hashCode();
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,9 @@
|
||||
package com.gildedrose.itemsorts;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem.QualityItemSkeleton;
|
||||
|
||||
public class Sulfuras extends QualityItemSkeleton implements QualityItem {
|
||||
public Sulfuras(String name, int sellIn, int quality) {
|
||||
super(name, sellIn, quality);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,10 @@
|
||||
package com.gildedrose.itemtorequest;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingRequest;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
|
||||
public class ProcessingRequestFromQualityItem {
|
||||
public <T extends QualityItem> ProcessingRequest<T> get(T qualityItem) {
|
||||
return new ProcessingRequest<>(qualityItem.getSellIn(), qualityItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.AgedBrie;
|
||||
|
||||
public class AgedBrieFromProcessingResponse implements QualityItemFromProcessingResponse<AgedBrie> {
|
||||
@Override
|
||||
public AgedBrie toQualityItem(AgedBrie qualityItemOld, ProcessingResponse<AgedBrie> processingResponse) {
|
||||
return new AgedBrie(qualityItemOld.getName(), processingResponse.getSellIn(), processingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.BackstagePass;
|
||||
|
||||
public class BackstagePassFromProcessingResponse implements QualityItemFromProcessingResponse<BackstagePass> {
|
||||
@Override
|
||||
public BackstagePass toQualityItem(BackstagePass qualityItemOld, ProcessingResponse<BackstagePass> processingResponse) {
|
||||
return new BackstagePass(qualityItemOld.getName(), processingResponse.getSellIn(), processingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.ConjuredItem;
|
||||
|
||||
public class ConjuredItemFromProcessingResponse implements QualityItemFromProcessingResponse<ConjuredItem> {
|
||||
@Override
|
||||
public ConjuredItem toQualityItem(ConjuredItem qualityItemOld, ProcessingResponse<ConjuredItem> processingResponse) {
|
||||
return new ConjuredItem(qualityItemOld.getName(), processingResponse.getSellIn(), processingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,12 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
|
||||
|
||||
public class NormalItemFromProcessingResponse implements QualityItemFromProcessingResponse<NormalItem> {
|
||||
@Override
|
||||
public NormalItem toQualityItem(NormalItem qualityItemOld, ProcessingResponse<NormalItem> processingResponse) {
|
||||
return new NormalItem(qualityItemOld.getName(), processingResponse.getSellIn(), processingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,8 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
|
||||
public interface QualityItemFromProcessingResponse<T extends QualityItem> {
|
||||
T toQualityItem(T qualityItemOld, ProcessingResponse<T> processingResponse);
|
||||
}
|
||||
@ -0,0 +1,44 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import lombok.AllArgsConstructor;
|
||||
import lombok.Getter;
|
||||
|
||||
import java.util.HashMap;
|
||||
import java.util.List;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
public class QualityItemFromProcessingResponseFactory {
|
||||
static final String EXCEPTION_MESSAGE_TEMPLATE = "QualityItemFromProcessingResponse for the item of type %s is not found. Make sure that the factory" +
|
||||
"is configured correctly";
|
||||
|
||||
Map<Class<? extends QualityItem>, QualityItemFromProcessingResponse<? extends QualityItem>> qualityItemFromProcessingResponseMap = new HashMap<>();
|
||||
|
||||
public <T extends QualityItem> QualityItemFromProcessingResponse<T> get(T qualityItem) {
|
||||
Class<? extends QualityItem> aClass = qualityItem.getClass();
|
||||
QualityItemFromProcessingResponse<? extends QualityItem> qualityItemProcessor = Optional.ofNullable(qualityItemFromProcessingResponseMap.get(aClass))
|
||||
.orElseThrow(
|
||||
() -> new IllegalArgumentException(String.format(EXCEPTION_MESSAGE_TEMPLATE, aClass)));
|
||||
@SuppressWarnings("unchecked")
|
||||
QualityItemFromProcessingResponse<T> qualityItemFromProcessingResponse =
|
||||
(QualityItemFromProcessingResponse<T>) qualityItemProcessor;
|
||||
return qualityItemFromProcessingResponse;
|
||||
}
|
||||
|
||||
|
||||
@Getter
|
||||
@AllArgsConstructor
|
||||
public static class QualityItemFromProcessingResponseFactoryItem<T extends QualityItem> {
|
||||
private final Class<T> itemType;
|
||||
private final QualityItemFromProcessingResponse<T> itemProcessor;
|
||||
}
|
||||
|
||||
public QualityItemFromProcessingResponseFactory(List<QualityItemFromProcessingResponseFactoryItem<?>> qualityItemFromProcessingResponseFactoryItems) {
|
||||
qualityItemFromProcessingResponseFactoryItems.forEach(qualityItemFromProcessingResponseFactoryItem ->
|
||||
qualityItemFromProcessingResponseMap.put(
|
||||
qualityItemFromProcessingResponseFactoryItem.getItemType(),
|
||||
qualityItemFromProcessingResponseFactoryItem.getItemProcessor())
|
||||
);
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,11 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
|
||||
public class SulfurasFromProcessingResponse implements QualityItemFromProcessingResponse<Sulfuras> {
|
||||
@Override
|
||||
public Sulfuras toQualityItem(Sulfuras qualityItemOld, ProcessingResponse<Sulfuras> processingResponse) {
|
||||
return new Sulfuras(qualityItemOld.getName(), processingResponse.getSellIn(), processingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -1,17 +1,94 @@
|
||||
package com.gildedrose;
|
||||
|
||||
import com.gildedrose.itemprocessors.AgedBrieProcessor;
|
||||
import com.gildedrose.itemprocessors.BackstagePassProcessor;
|
||||
import com.gildedrose.itemprocessors.ConjuredItemProcessor;
|
||||
import com.gildedrose.itemprocessors.NormalItemProcessor;
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory;
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory.ProcessorFactoryItem;
|
||||
import com.gildedrose.itemprocessors.SulfurasProcessor;
|
||||
import com.gildedrose.itemsorts.AgedBrie;
|
||||
import com.gildedrose.itemsorts.BackstagePass;
|
||||
import com.gildedrose.itemsorts.ConjuredItem;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
import com.gildedrose.itemtorequest.ProcessingRequestFromQualityItem;
|
||||
import com.gildedrose.responsetoitem.AgedBrieFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.BackstagePassFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.ConjuredItemFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.NormalItemFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory.QualityItemFromProcessingResponseFactoryItem;
|
||||
import com.gildedrose.responsetoitem.SulfurasFromProcessingResponse;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
|
||||
class GildedRoseTest {
|
||||
|
||||
@Test
|
||||
void foo() {
|
||||
Item[] items = new Item[] { new Item("foo", 0, 0) };
|
||||
GildedRose app = new GildedRose(items);
|
||||
List<QualityItem> items = new ArrayList<>();
|
||||
items.add(new NormalItem("foo", 0, 0));
|
||||
|
||||
List<ProcessorFactoryItem<?>> processorFactoryItems = Arrays.asList(
|
||||
new ProcessorFactoryItem<>(NormalItem.class, new NormalItemProcessor()),
|
||||
new ProcessorFactoryItem<>(AgedBrie.class, new AgedBrieProcessor()),
|
||||
new ProcessorFactoryItem<>(Sulfuras.class, new SulfurasProcessor()),
|
||||
new ProcessorFactoryItem<>(BackstagePass.class, new BackstagePassProcessor()),
|
||||
new ProcessorFactoryItem<>(ConjuredItem.class, new ConjuredItemProcessor()));
|
||||
ProcessorFactory processorFactory = new ProcessorFactory(processorFactoryItems);
|
||||
|
||||
List<QualityItemFromProcessingResponseFactoryItem<?>> qualityItemFromProcessingResponseFactoryItems = Arrays.asList(
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(NormalItem.class, new NormalItemFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(AgedBrie.class, new AgedBrieFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(Sulfuras.class, new SulfurasFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(BackstagePass.class, new BackstagePassFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(ConjuredItem.class, new ConjuredItemFromProcessingResponse()));
|
||||
QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactory =
|
||||
new QualityItemFromProcessingResponseFactory(qualityItemFromProcessingResponseFactoryItems);
|
||||
|
||||
ProcessingRequestFromQualityItem processingRequestFromQualityItem = new ProcessingRequestFromQualityItem();
|
||||
|
||||
QualityItemHandler qualityItemHandler = new QualityItemHandler(processorFactory, processingRequestFromQualityItem,
|
||||
qualityItemFromProcessingResponseFactory);
|
||||
|
||||
GildedRose app = new GildedRose(items, qualityItemHandler);
|
||||
app.updateQuality();
|
||||
assertEquals("fixme", app.items[0].name);
|
||||
assertEquals("foo", app.getItems().get(0).getName());
|
||||
}
|
||||
|
||||
/**
|
||||
* Check that {@link GildedRose#updateQuality()} will call {@link QualityItemHandler#processOneItem(QualityItem)}
|
||||
* for every element in the GildedRose
|
||||
*/
|
||||
@Test
|
||||
void updateQualityTest() {
|
||||
List<QualityItem> calledForItems = new ArrayList<>();
|
||||
List<QualityItem> inputItems = new ArrayList<>();
|
||||
NormalItem expectedItem1 = new NormalItem("name1", 1, 2);
|
||||
NormalItem expectedItem2 = new NormalItem("name2", 1, 2);
|
||||
inputItems.add(expectedItem1);
|
||||
inputItems.add(expectedItem2);
|
||||
|
||||
QualityItemHandler qualityItemHandler = new QualityItemHandler(null, null, null) {
|
||||
@Override
|
||||
QualityItem processOneItem(QualityItem qualityItem) {
|
||||
calledForItems.add(qualityItem);
|
||||
return qualityItem;
|
||||
}
|
||||
};
|
||||
GildedRose gildedRose = new GildedRose(inputItems, qualityItemHandler);
|
||||
|
||||
gildedRose.updateQuality();
|
||||
assertTrue(calledForItems.containsAll(inputItems));
|
||||
calledForItems.removeAll(inputItems);
|
||||
assertTrue(calledForItems.isEmpty());
|
||||
}
|
||||
}
|
||||
|
||||
@ -0,0 +1,55 @@
|
||||
package com.gildedrose;
|
||||
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory;
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingRequest;
|
||||
import com.gildedrose.itemtorequest.ProcessingRequestFromQualityItem;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.mockito.Mockito;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class QualityItemHandlerTest {
|
||||
|
||||
/**
|
||||
* Tests the chain of calls in the {@link QualityItemHandler#processOneItem(QualityItem)} method.
|
||||
*/
|
||||
@Test
|
||||
void updateQualityForOneItemTest() {
|
||||
ProcessorFactory processorFactoryMock = Mockito.mock(ProcessorFactory.class);
|
||||
ProcessingRequestFromQualityItem processingRequestFromQualityItemMock = Mockito.mock(ProcessingRequestFromQualityItem.class);
|
||||
QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactoryMock = Mockito.mock(QualityItemFromProcessingResponseFactory.class);
|
||||
|
||||
|
||||
QualityItemHandler qualityItemHandler = new QualityItemHandler(processorFactoryMock, processingRequestFromQualityItemMock, qualityItemFromProcessingResponseFactoryMock);
|
||||
QualityItem qualityItem = new NormalItem("name", 1, 1);
|
||||
QualityItem qualityItemResult = new NormalItem("result", 1, 1);
|
||||
|
||||
ProcessingRequest<QualityItem> expectedProcessingRequest = new ProcessingRequest<>(1, 2);
|
||||
Mockito.when(processingRequestFromQualityItemMock.get(qualityItem)).thenReturn(expectedProcessingRequest);
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
QualityItemProcessor<QualityItem> itemProcessorMock = (QualityItemProcessor<QualityItem>) Mockito.mock(QualityItemProcessor.class);
|
||||
Mockito.when(processorFactoryMock.get(qualityItem)).thenReturn(itemProcessorMock);
|
||||
|
||||
|
||||
ProcessingResponse<QualityItem> expectedProcessingResponse = new ProcessingResponse<>(1, 2);
|
||||
Mockito.when(itemProcessorMock.processItem(expectedProcessingRequest)).thenReturn(expectedProcessingResponse);
|
||||
|
||||
|
||||
@SuppressWarnings("unchecked")
|
||||
QualityItemFromProcessingResponse<QualityItem> qualityItemQualityItemFromProcessingResponse =
|
||||
(QualityItemFromProcessingResponse<QualityItem>) Mockito.mock(QualityItemFromProcessingResponse.class);
|
||||
Mockito.when(qualityItemFromProcessingResponseFactoryMock.get(qualityItem)).thenReturn(qualityItemQualityItemFromProcessingResponse);
|
||||
|
||||
Mockito.when(qualityItemQualityItemFromProcessingResponse.toQualityItem(qualityItem, expectedProcessingResponse))
|
||||
.thenReturn(qualityItemResult);
|
||||
|
||||
assertEquals(qualityItemResult, qualityItemHandler.processOneItem(qualityItem));
|
||||
}
|
||||
}
|
||||
@ -1,22 +1,70 @@
|
||||
package com.gildedrose;
|
||||
|
||||
import com.gildedrose.responsetoitem.AgedBrieFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.BackstagePassFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.ConjuredItemFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.NormalItemFromProcessingResponse;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory;
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory.QualityItemFromProcessingResponseFactoryItem;
|
||||
import com.gildedrose.responsetoitem.SulfurasFromProcessingResponse;
|
||||
import com.gildedrose.itemprocessors.AgedBrieProcessor;
|
||||
import com.gildedrose.itemprocessors.BackstagePassProcessor;
|
||||
import com.gildedrose.itemprocessors.ConjuredItemProcessor;
|
||||
import com.gildedrose.itemprocessors.NormalItemProcessor;
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory;
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory.ProcessorFactoryItem;
|
||||
import com.gildedrose.itemtorequest.ProcessingRequestFromQualityItem;
|
||||
import com.gildedrose.itemprocessors.SulfurasProcessor;
|
||||
import com.gildedrose.itemsorts.AgedBrie;
|
||||
import com.gildedrose.itemsorts.BackstagePass;
|
||||
import com.gildedrose.itemsorts.ConjuredItem;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
|
||||
import java.util.Arrays;
|
||||
import java.util.List;
|
||||
|
||||
public class TexttestFixture {
|
||||
public static void main(String[] args) {
|
||||
System.out.println("OMGHAI!");
|
||||
|
||||
Item[] items = new Item[] {
|
||||
new Item("+5 Dexterity Vest", 10, 20), //
|
||||
new Item("Aged Brie", 2, 0), //
|
||||
new Item("Elixir of the Mongoose", 5, 7), //
|
||||
new Item("Sulfuras, Hand of Ragnaros", 0, 80), //
|
||||
new Item("Sulfuras, Hand of Ragnaros", -1, 80),
|
||||
new Item("Backstage passes to a TAFKAL80ETC concert", 15, 20),
|
||||
new Item("Backstage passes to a TAFKAL80ETC concert", 10, 49),
|
||||
new Item("Backstage passes to a TAFKAL80ETC concert", 5, 49),
|
||||
List<QualityItem> items = Arrays.asList(
|
||||
new NormalItem("+5 Dexterity Vest", 10, 20), //
|
||||
new AgedBrie("Aged Brie", 2, 0), //
|
||||
new NormalItem("Elixir of the Mongoose", 5, 7), //
|
||||
new Sulfuras("Sulfuras, Hand of Ragnaros", 0, 80), //
|
||||
new Sulfuras("Sulfuras, Hand of Ragnaros", -1, 80),
|
||||
new BackstagePass("Backstage passes to a TAFKAL80ETC concert", 15, 20),
|
||||
new BackstagePass("Backstage passes to a TAFKAL80ETC concert", 10, 49),
|
||||
new BackstagePass("Backstage passes to a TAFKAL80ETC concert", 5, 49),
|
||||
// this conjured item does not work properly yet
|
||||
new Item("Conjured Mana Cake", 3, 6) };
|
||||
new ConjuredItem("Conjured Mana Cake", 3, 6)
|
||||
);
|
||||
|
||||
GildedRose app = new GildedRose(items);
|
||||
List<ProcessorFactoryItem<?>> processorFactoryItems = Arrays.asList(
|
||||
new ProcessorFactoryItem<>(NormalItem.class, new NormalItemProcessor()),
|
||||
new ProcessorFactoryItem<>(AgedBrie.class, new AgedBrieProcessor()),
|
||||
new ProcessorFactoryItem<>(Sulfuras.class, new SulfurasProcessor()),
|
||||
new ProcessorFactoryItem<>(BackstagePass.class, new BackstagePassProcessor()),
|
||||
new ProcessorFactoryItem<>(ConjuredItem.class, new ConjuredItemProcessor()));
|
||||
ProcessorFactory processorFactory = new ProcessorFactory(processorFactoryItems);
|
||||
|
||||
List<QualityItemFromProcessingResponseFactoryItem<?>> qualityItemFromProcessingResponseFactoryItems = Arrays.asList(
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(NormalItem.class, new NormalItemFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(AgedBrie.class, new AgedBrieFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(Sulfuras.class, new SulfurasFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(BackstagePass.class, new BackstagePassFromProcessingResponse()),
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(ConjuredItem.class, new ConjuredItemFromProcessingResponse()));
|
||||
QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactory =
|
||||
new QualityItemFromProcessingResponseFactory(qualityItemFromProcessingResponseFactoryItems);
|
||||
|
||||
ProcessingRequestFromQualityItem processingRequestFromQualityItem = new ProcessingRequestFromQualityItem();
|
||||
|
||||
QualityItemHandler qualityItemHandler = new QualityItemHandler(processorFactory, processingRequestFromQualityItem,
|
||||
qualityItemFromProcessingResponseFactory);
|
||||
|
||||
GildedRose app = new GildedRose(items, qualityItemHandler);
|
||||
|
||||
int days = 2;
|
||||
if (args.length > 0) {
|
||||
@ -26,7 +74,7 @@ public class TexttestFixture {
|
||||
for (int i = 0; i < days; i++) {
|
||||
System.out.println("-------- day " + i + " --------");
|
||||
System.out.println("name, sellIn, quality");
|
||||
for (Item item : items) {
|
||||
for (QualityItem item : items) {
|
||||
System.out.println(item);
|
||||
}
|
||||
System.out.println();
|
||||
|
||||
@ -0,0 +1,15 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class AgedBrieProcessorTest {
|
||||
@Test
|
||||
public void test(){
|
||||
AgedBrieProcessor agedBrieProcessor = new AgedBrieProcessor();
|
||||
int oldQuality = 3;
|
||||
int qualityChange = 4;
|
||||
assertEquals(oldQuality + qualityChange, agedBrieProcessor.qualityFunction(oldQuality, qualityChange));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,38 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
import org.junit.jupiter.params.provider.MethodSource;
|
||||
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import static com.gildedrose.itemprocessors.BackstagePassProcessor.FIVE_DAYS_BEFORE_CONCERT;
|
||||
import static com.gildedrose.itemprocessors.BackstagePassProcessor.TEN_DAYS_BEFORE_CONCERT;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class BackstagePassProcessorTest {
|
||||
@Test
|
||||
public void test() {
|
||||
BackstagePassProcessor backstagePassProcessor = new BackstagePassProcessor();
|
||||
int oldQuality = 33;
|
||||
int newQuality = 88;
|
||||
assertEquals(oldQuality + newQuality, backstagePassProcessor.qualityFunction(oldQuality, newQuality));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
public static Stream<Arguments> calculateQualityChangeValues() {
|
||||
return Stream.of(
|
||||
Arguments.of(-1, 77, -77) ,
|
||||
Arguments.of(FIVE_DAYS_BEFORE_CONCERT - 1, 77, 3),
|
||||
Arguments.of(TEN_DAYS_BEFORE_CONCERT - 1, 77, 2),
|
||||
Arguments.of(TEN_DAYS_BEFORE_CONCERT, 77, 1)
|
||||
);
|
||||
}
|
||||
@MethodSource("calculateQualityChangeValues")
|
||||
@ParameterizedTest
|
||||
public void calculateQualityChangeTest(int sellIn, int oldQuality, int expectedQualityChange) {
|
||||
BackstagePassProcessor backstagePassProcessor = new BackstagePassProcessor();
|
||||
assertEquals(expectedQualityChange, backstagePassProcessor.calculateQualityChange(sellIn, oldQuality));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,17 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static com.gildedrose.itemprocessors.ConjuredItemProcessor.CONJURED_ITEM_QUALITY_CHANGE_MULTIPLIER;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class ConjuredItemProcessorTest {
|
||||
|
||||
@Test
|
||||
void calculateQualityChange() {
|
||||
ConjuredItemProcessor conjuredItemProcessor = new ConjuredItemProcessor();
|
||||
int qualityChange = 77;
|
||||
assertEquals(qualityChange * CONJURED_ITEM_QUALITY_CHANGE_MULTIPLIER,
|
||||
conjuredItemProcessor.applyQualityChangeMultiplier(qualityChange));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,39 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.ProcessorFactory.ProcessorFactoryItem;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.mockito.Mockito;
|
||||
|
||||
|
||||
import java.util.Collections;
|
||||
|
||||
import static com.gildedrose.itemprocessors.ProcessorFactory.EXCEPTION_MESSAGE_TEMPLATE;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
|
||||
class ProcessorFactoryTest {
|
||||
|
||||
@Test
|
||||
public void testFactoryCannotHandleItem() {
|
||||
ProcessorFactory processorFactory = new ProcessorFactory(Collections.emptyList());
|
||||
QualityItem itemThatCannotBeProcessed = Mockito.mock(QualityItem.class);
|
||||
boolean exceptionWasThrown = false;
|
||||
try {
|
||||
processorFactory.get(itemThatCannotBeProcessed);
|
||||
} catch (IllegalArgumentException e) {
|
||||
exceptionWasThrown = true;
|
||||
assertEquals(String.format(EXCEPTION_MESSAGE_TEMPLATE, itemThatCannotBeProcessed.getClass()), e.getMessage());
|
||||
}
|
||||
assertTrue(exceptionWasThrown);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFactoryCanHandleItem() {
|
||||
QualityItemProcessor<NormalItem> normalItemProcessor = new NormalItemProcessor();
|
||||
NormalItem normalItem = new NormalItem("name", 1, 2);
|
||||
ProcessorFactory processorFactory = new ProcessorFactory(Collections.singletonList(new ProcessorFactoryItem<>(NormalItem.class, normalItemProcessor)));
|
||||
assertEquals(normalItemProcessor, processorFactory.get(normalItem));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,142 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingRequest;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.junit.jupiter.params.ParameterizedTest;
|
||||
import org.junit.jupiter.params.provider.Arguments;
|
||||
import org.junit.jupiter.params.provider.MethodSource;
|
||||
|
||||
import java.util.stream.Stream;
|
||||
|
||||
import static com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton.MAX_QUALITY;
|
||||
import static com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton.MIN_QUALITY;
|
||||
import static com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton.QUALITY_CHANGE_AFTER_SELL_DATE;
|
||||
import static com.gildedrose.itemprocessors.QualityItemProcessor.QualityItemProcessorSkeleton.QUALITY_CHANGE_BEFORE_SELL_DATE;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class QualityItemProcessorTest {
|
||||
|
||||
|
||||
@Test
|
||||
public void testCalculateItem() {
|
||||
final int oldQualityExpected = 3;
|
||||
final int oldSellInExpected = 27;
|
||||
final int newSellInExpected = 509;
|
||||
final int newQualityExpected = 99;
|
||||
NormalItem testItem = new NormalItem("test item", oldSellInExpected, oldQualityExpected);
|
||||
|
||||
ProcessingRequest<QualityItem> qualityItemProcessingRequest = new ProcessingRequest<>(testItem.getSellIn(), testItem.getQuality());
|
||||
ProcessingResponse<QualityItem> qualityItemProcessingResponse = new ProcessingResponse<>(newSellInExpected, newQualityExpected);
|
||||
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {
|
||||
@Override
|
||||
int calculateNewSellIn(int oldSellIn) {
|
||||
assertEquals(oldSellInExpected, oldSellIn);
|
||||
return newSellInExpected;
|
||||
}
|
||||
|
||||
@Override
|
||||
int calculateNewQuality(int newSellIn, int oldQuality) {
|
||||
assertEquals(oldQualityExpected, oldQuality);
|
||||
assertEquals(newSellInExpected, newSellIn);
|
||||
return newQualityExpected;
|
||||
}
|
||||
};
|
||||
assertEquals(qualityItemProcessingResponse, qualityItemProcessorSkeleton.processItem(qualityItemProcessingRequest));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void calculateNewSellInTest() {
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {
|
||||
};
|
||||
int oldSellIn = 1;
|
||||
assertEquals(0, qualityItemProcessorSkeleton.calculateNewSellIn(oldSellIn));
|
||||
}
|
||||
|
||||
@Test
|
||||
public void calculateNewQuality() {
|
||||
int oldQualityExpected = 3;
|
||||
int newSellInExpected = 4;
|
||||
int qualityChangeExpected = 77;
|
||||
int resultOfQualityFunctionExpected = 300;
|
||||
int qualityLimitsCheckExpected = 777;
|
||||
int qualityChangeAfterQualityChangeMultiplierWasApplied = 389;
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {
|
||||
@Override
|
||||
int calculateQualityChange(int sellIn, int oldQuality) {
|
||||
assertEquals(oldQualityExpected, oldQuality);
|
||||
assertEquals(newSellInExpected, sellIn);
|
||||
return qualityChangeExpected;
|
||||
}
|
||||
|
||||
@Override
|
||||
int applyQualityChangeMultiplier(int qualityChange) {
|
||||
assertEquals(qualityChangeExpected, qualityChange);
|
||||
return qualityChangeAfterQualityChangeMultiplierWasApplied;
|
||||
}
|
||||
|
||||
@Override
|
||||
int qualityFunction(int oldQuality, int qualityChange) {
|
||||
assertEquals(oldQualityExpected, oldQuality);
|
||||
assertEquals(qualityChangeAfterQualityChangeMultiplierWasApplied, qualityChange);
|
||||
return resultOfQualityFunctionExpected;
|
||||
}
|
||||
|
||||
|
||||
@Override
|
||||
int qualityLimitsCheck(int quality) {
|
||||
assertEquals(resultOfQualityFunctionExpected, quality);
|
||||
return qualityLimitsCheckExpected;
|
||||
}
|
||||
};
|
||||
|
||||
assertEquals(qualityLimitsCheckExpected, qualityItemProcessorSkeleton.calculateNewQuality(newSellInExpected, oldQualityExpected));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
public static Stream<Arguments> qualityChangeTestValues() {
|
||||
return Stream.of(
|
||||
Arguments.of(-1, QUALITY_CHANGE_AFTER_SELL_DATE),
|
||||
Arguments.of(0, QUALITY_CHANGE_BEFORE_SELL_DATE)
|
||||
);
|
||||
}
|
||||
|
||||
@MethodSource("qualityChangeTestValues")
|
||||
@ParameterizedTest
|
||||
public void calculateQualityChangeTest(int sellIn, int expectedChange) {
|
||||
int oldQuality = 333;
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {};
|
||||
assertEquals(expectedChange, qualityItemProcessorSkeleton.calculateQualityChange(sellIn, oldQuality));
|
||||
}
|
||||
|
||||
@Test
|
||||
void testQualityFunctionTest() {
|
||||
int oldQuality = 333;
|
||||
int qualityChange = 77;
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {};
|
||||
assertEquals(oldQuality - qualityChange, qualityItemProcessorSkeleton.qualityFunction(oldQuality, qualityChange));
|
||||
}
|
||||
|
||||
@SuppressWarnings("unused")
|
||||
public static Stream<Arguments> qualityLimitCheckValues() {
|
||||
int between_max_and_min = (MAX_QUALITY + MIN_QUALITY) / 2;
|
||||
return Stream.of(
|
||||
Arguments.of(MAX_QUALITY + 1, MAX_QUALITY),
|
||||
Arguments.of(MIN_QUALITY - 1, MIN_QUALITY),
|
||||
Arguments.of(between_max_and_min, between_max_and_min)
|
||||
);
|
||||
}
|
||||
|
||||
@MethodSource("qualityLimitCheckValues")
|
||||
@ParameterizedTest
|
||||
void qualityLimitsCheckTest(int quality, int resultingQuality) {
|
||||
QualityItemProcessorSkeleton<QualityItem> qualityItemProcessorSkeleton = new QualityItemProcessorSkeleton<QualityItem>() {};
|
||||
assertEquals(resultingQuality, qualityItemProcessorSkeleton.qualityLimitsCheck(quality));
|
||||
}
|
||||
|
||||
|
||||
}
|
||||
@ -0,0 +1,19 @@
|
||||
package com.gildedrose.itemprocessors;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingRequest;
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.*;
|
||||
|
||||
class SulfurasProcessorTest {
|
||||
@Test
|
||||
void processItem() {
|
||||
SulfurasProcessor sulfurasProcessor = new SulfurasProcessor();
|
||||
ProcessingRequest<Sulfuras> sulfurasProcessingRequest = new ProcessingRequest<>(3, 4);
|
||||
ProcessingResponse<Sulfuras> sulfurasProcessingResponse = sulfurasProcessor.processItem(sulfurasProcessingRequest);
|
||||
assertEquals(sulfurasProcessingRequest.getSellIn(), sulfurasProcessingResponse.getSellIn());
|
||||
assertEquals(sulfurasProcessingRequest.getQuality(), sulfurasProcessingResponse.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,19 @@
|
||||
package com.gildedrose.itemtorequest;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingRequest;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class ProcessingRequestFromQualityItemTest {
|
||||
@Test
|
||||
void get() {
|
||||
ProcessingRequestFromQualityItem processingRequestFromQualityItem = new ProcessingRequestFromQualityItem();
|
||||
int sellIn = 99;
|
||||
int quality = 938;
|
||||
NormalItem normalItem = new NormalItem("name", sellIn, quality);
|
||||
ProcessingRequest<NormalItem> expectedProcessingRequest = new ProcessingRequest<>(sellIn, quality);
|
||||
assertEquals(expectedProcessingRequest, processingRequestFromQualityItem.get(normalItem));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.AgedBrie;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class AgedBrieFromProcessingResponseTest {
|
||||
|
||||
@Test
|
||||
void toQualityItem() {
|
||||
AgedBrieFromProcessingResponse agedBrieFromProcessingResponse = new AgedBrieFromProcessingResponse();
|
||||
AgedBrie oldItem = new AgedBrie("name", 1, 2);
|
||||
ProcessingResponse<AgedBrie> processingResponse = new ProcessingResponse<>(7, 8);
|
||||
AgedBrie newItem = agedBrieFromProcessingResponse.toQualityItem(oldItem, processingResponse);
|
||||
assertEquals(oldItem.getName(), newItem.getName());
|
||||
assertEquals(processingResponse.getSellIn(), newItem.getSellIn());
|
||||
assertEquals(processingResponse.getQuality(), newItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.BackstagePass;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class BackstagePassFromProcessingResponseTest {
|
||||
|
||||
@Test
|
||||
void toQualityItem() {
|
||||
BackstagePassFromProcessingResponse qualityItemFromProcessingResponse = new BackstagePassFromProcessingResponse();
|
||||
BackstagePass oldItem = new BackstagePass("name", 1, 2);
|
||||
ProcessingResponse<BackstagePass> processingResponse = new ProcessingResponse<>(7, 8);
|
||||
BackstagePass newItem = qualityItemFromProcessingResponse.toQualityItem(oldItem, processingResponse);
|
||||
assertEquals(oldItem.getName(), newItem.getName());
|
||||
assertEquals(processingResponse.getSellIn(), newItem.getSellIn());
|
||||
assertEquals(processingResponse.getQuality(), newItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.ConjuredItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class ConjuredItemFromProcessingResponseTest {
|
||||
|
||||
@Test
|
||||
void toQualityItem() {
|
||||
ConjuredItemFromProcessingResponse qualityItemFromProcessingResponse = new ConjuredItemFromProcessingResponse();
|
||||
ConjuredItem oldItem = new ConjuredItem("name", 1, 2);
|
||||
ProcessingResponse<ConjuredItem> processingResponse = new ProcessingResponse<>(7, 8);
|
||||
ConjuredItem newItem = qualityItemFromProcessingResponse.toQualityItem(oldItem, processingResponse);
|
||||
assertEquals(oldItem.getName(), newItem.getName());
|
||||
assertEquals(processingResponse.getSellIn(), newItem.getSellIn());
|
||||
assertEquals(processingResponse.getQuality(), newItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class NormalItemFromProcessingResponseTest {
|
||||
|
||||
@Test
|
||||
void toQualityItem() {
|
||||
NormalItemFromProcessingResponse qualityItemFromProcessingResponse = new NormalItemFromProcessingResponse();
|
||||
NormalItem oldItem = new NormalItem("name", 1, 2);
|
||||
ProcessingResponse<NormalItem> processingResponse = new ProcessingResponse<>(7, 8);
|
||||
NormalItem newItem = qualityItemFromProcessingResponse.toQualityItem(oldItem, processingResponse);
|
||||
assertEquals(oldItem.getName(), newItem.getName());
|
||||
assertEquals(processingResponse.getSellIn(), newItem.getSellIn());
|
||||
assertEquals(processingResponse.getQuality(), newItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,40 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory.QualityItemFromProcessingResponseFactoryItem;
|
||||
import com.gildedrose.itemsorts.NormalItem;
|
||||
import com.gildedrose.itemsorts.QualityItem;
|
||||
import org.junit.jupiter.api.Test;
|
||||
import org.mockito.Mockito;
|
||||
|
||||
import java.util.Collections;
|
||||
|
||||
import static com.gildedrose.responsetoitem.QualityItemFromProcessingResponseFactory.EXCEPTION_MESSAGE_TEMPLATE;
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
import static org.junit.jupiter.api.Assertions.assertTrue;
|
||||
|
||||
class QualityItemFromProcessingResponseFactoryTest {
|
||||
@Test
|
||||
public void testFactoryCannotHandleAnItem() {
|
||||
QualityItemFromProcessingResponseFactory factory = new QualityItemFromProcessingResponseFactory(Collections.emptyList());
|
||||
QualityItem itemThatCannotBeProcessed = Mockito.mock(QualityItem.class);
|
||||
boolean exceptionWasThrown = false;
|
||||
try {
|
||||
factory.get(itemThatCannotBeProcessed);
|
||||
} catch (IllegalArgumentException e) {
|
||||
exceptionWasThrown = true;
|
||||
assertEquals(String.format(EXCEPTION_MESSAGE_TEMPLATE, itemThatCannotBeProcessed.getClass()), e.getMessage());
|
||||
}
|
||||
assertTrue(exceptionWasThrown);
|
||||
}
|
||||
|
||||
@Test
|
||||
public void testFactoryCanHandleAnItem() {
|
||||
QualityItemFromProcessingResponse<NormalItem> normalItemProcessor = new NormalItemFromProcessingResponse();
|
||||
NormalItem normalItem = new NormalItem("name", 1, 2);
|
||||
QualityItemFromProcessingResponseFactory qualityItemFromProcessingResponseFactory =
|
||||
new QualityItemFromProcessingResponseFactory(Collections.singletonList(
|
||||
new QualityItemFromProcessingResponseFactoryItem<>(NormalItem.class, normalItemProcessor)
|
||||
));
|
||||
assertEquals(normalItemProcessor, qualityItemFromProcessingResponseFactory.get(normalItem));
|
||||
}
|
||||
}
|
||||
@ -0,0 +1,21 @@
|
||||
package com.gildedrose.responsetoitem;
|
||||
|
||||
import com.gildedrose.itemprocessors.QualityItemProcessor.ProcessingResponse;
|
||||
import com.gildedrose.itemsorts.Sulfuras;
|
||||
import org.junit.jupiter.api.Test;
|
||||
|
||||
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||
|
||||
class SulfurasFromProcessingResponseTest {
|
||||
|
||||
@Test
|
||||
void toQualityItem() {
|
||||
SulfurasFromProcessingResponse qualityItemFromProcessingResponse = new SulfurasFromProcessingResponse();
|
||||
Sulfuras oldItem = new Sulfuras("name", 1, 2);
|
||||
ProcessingResponse<Sulfuras> processingResponse = new ProcessingResponse<>(7, 8);
|
||||
Sulfuras newItem = qualityItemFromProcessingResponse.toQualityItem(oldItem, processingResponse);
|
||||
assertEquals(oldItem.getName(), newItem.getName());
|
||||
assertEquals(processingResponse.getSellIn(), newItem.getSellIn());
|
||||
assertEquals(processingResponse.getQuality(), newItem.getQuality());
|
||||
}
|
||||
}
|
||||
@ -21,7 +21,7 @@ Sulfuras, Hand of Ragnaros, -1, 80
|
||||
Backstage passes to a TAFKAL80ETC concert, 14, 21
|
||||
Backstage passes to a TAFKAL80ETC concert, 9, 50
|
||||
Backstage passes to a TAFKAL80ETC concert, 4, 50
|
||||
Conjured Mana Cake, 2, 5
|
||||
Conjured Mana Cake, 2, 4
|
||||
|
||||
-------- day 2 --------
|
||||
name, sellIn, quality
|
||||
@ -33,7 +33,7 @@ Sulfuras, Hand of Ragnaros, -1, 80
|
||||
Backstage passes to a TAFKAL80ETC concert, 13, 22
|
||||
Backstage passes to a TAFKAL80ETC concert, 8, 50
|
||||
Backstage passes to a TAFKAL80ETC concert, 3, 50
|
||||
Conjured Mana Cake, 1, 4
|
||||
Conjured Mana Cake, 1, 2
|
||||
|
||||
-------- day 3 --------
|
||||
name, sellIn, quality
|
||||
@ -45,7 +45,7 @@ Sulfuras, Hand of Ragnaros, -1, 80
|
||||
Backstage passes to a TAFKAL80ETC concert, 12, 23
|
||||
Backstage passes to a TAFKAL80ETC concert, 7, 50
|
||||
Backstage passes to a TAFKAL80ETC concert, 2, 50
|
||||
Conjured Mana Cake, 0, 3
|
||||
Conjured Mana Cake, 0, 0
|
||||
|
||||
-------- day 4 --------
|
||||
name, sellIn, quality
|
||||
@ -57,7 +57,7 @@ Sulfuras, Hand of Ragnaros, -1, 80
|
||||
Backstage passes to a TAFKAL80ETC concert, 11, 24
|
||||
Backstage passes to a TAFKAL80ETC concert, 6, 50
|
||||
Backstage passes to a TAFKAL80ETC concert, 1, 50
|
||||
Conjured Mana Cake, -1, 1
|
||||
Conjured Mana Cake, -1, 0
|
||||
|
||||
-------- day 5 --------
|
||||
name, sellIn, quality
|
||||
|
||||
@ -1,4 +1,5 @@
|
||||
full_name:Gilded Rose Refactoring Kata
|
||||
home_operating_system:posix
|
||||
|
||||
# set your preferred editor and diff tool.
|
||||
view_program:subl
|
||||
@ -12,8 +13,8 @@ diff_program:meld
|
||||
#executable:${TEXTTEST_HOME}/cpp/cmake-build-debug/test/cpp_texttest/GildedRoseTextTests
|
||||
|
||||
# Settings for the Java version
|
||||
#executable:com.gildedrose.TexttestFixture
|
||||
#interpreter:java
|
||||
executable:com.gildedrose.TexttestFixture
|
||||
interpreter:java
|
||||
# note you'll also need to update the file environment.gr with your classpath if you keep your classfiles somewhere unusual
|
||||
|
||||
# Settings for the Ruby version
|
||||
|
||||
Loading…
Reference in New Issue
Block a user