diff --git a/app/Module.java b/app/Module.java index f622b4cd6..b7508dd87 100644 --- a/app/Module.java +++ b/app/Module.java @@ -1,19 +1,9 @@ -import com.commercetools.sunrise.cms.CmsService; import com.commercetools.sunrise.ctp.categories.CachedCategoryTreeProvider; import com.commercetools.sunrise.ctp.categories.CategoriesSettings; import com.commercetools.sunrise.ctp.categories.NavigationCategoryTree; import com.commercetools.sunrise.ctp.categories.NewCategoryTree; import com.commercetools.sunrise.email.EmailSender; -import com.commercetools.sunrise.framework.controllers.metrics.SimpleMetricsSphereClientProvider; import com.commercetools.sunrise.framework.injection.RequestScoped; -import com.commercetools.sunrise.framework.localization.CountryFromSessionProvider; -import com.commercetools.sunrise.framework.localization.CurrencyFromCountryProvider; -import com.commercetools.sunrise.framework.localization.LocaleFromUrlProvider; -import com.commercetools.sunrise.framework.template.cms.FileBasedCmsServiceProvider; -import com.commercetools.sunrise.framework.template.engine.HandlebarsTemplateEngineProvider; -import com.commercetools.sunrise.framework.template.engine.TemplateEngine; -import com.commercetools.sunrise.framework.template.i18n.ConfigurableI18nResolverProvider; -import com.commercetools.sunrise.framework.template.i18n.I18nResolver; import com.commercetools.sunrise.framework.viewmodels.content.carts.MiniCartViewModelFactory; import com.commercetools.sunrise.httpauth.HttpAuthentication; import com.commercetools.sunrise.httpauth.basic.BasicAuthenticationProvider; @@ -61,11 +51,6 @@ public class Module extends AbstractModule { @Override protected void configure() { - // Binding for the client to connect commercetools - bind(SphereClient.class) - .toProvider(SimpleMetricsSphereClientProvider.class) - .in(Singleton.class); - // Binding for the HTTP Authentication bind(HttpAuthentication.class) .toProvider(BasicAuthenticationProvider.class) @@ -74,33 +59,11 @@ protected void configure() { // Binding for category tree bind(CategoryTree.class).toProvider(CachedCategoryTreeProvider.class); - // Binding for all template related, such as the engine, CMS and i18n - bind(CmsService.class) - .toProvider(FileBasedCmsServiceProvider.class) - .in(Singleton.class); - bind(TemplateEngine.class) - .toProvider(HandlebarsTemplateEngineProvider.class) - .in(Singleton.class); - bind(I18nResolver.class) - .toProvider(ConfigurableI18nResolverProvider.class) - .in(Singleton.class); - // Bindings fo email sender bind(EmailSender.class) .toProvider(EmailSenderProvider.class) .in(Singleton.class); - // Bindings for all user context related - bind(Locale.class) - .toProvider(LocaleFromUrlProvider.class) - .in(RequestScoped.class); - bind(CountryCode.class) - .toProvider(CountryFromSessionProvider.class) - .in(RequestScoped.class); - bind(CurrencyUnit.class) - .toProvider(CurrencyFromCountryProvider.class) - .in(RequestScoped.class); - // Bindings for the configured faceted search mappers bind(TermFacetViewModelFactory.class) .annotatedWith(Names.named("alphabeticallySorted")) diff --git a/common/app/com/commercetools/sunrise/common/localization/LocalizationSelectorViewModelFactory.java b/common/app/com/commercetools/sunrise/common/localization/LocalizationSelectorViewModelFactory.java index a0daed772..7532938df 100644 --- a/common/app/com/commercetools/sunrise/common/localization/LocalizationSelectorViewModelFactory.java +++ b/common/app/com/commercetools/sunrise/common/localization/LocalizationSelectorViewModelFactory.java @@ -5,7 +5,7 @@ import com.commercetools.sunrise.framework.viewmodels.SimpleViewModelFactory; import com.commercetools.sunrise.framework.viewmodels.forms.countries.CountryFormSelectableOptionViewModel; import com.commercetools.sunrise.framework.viewmodels.forms.countries.CountryFormSelectableOptionViewModelFactory; -import com.commercetools.sunrise.framework.localization.ProjectContext; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.injection.RequestScoped; import com.neovisionaries.i18n.CountryCode; diff --git a/common/app/com/commercetools/sunrise/ctp/client/SphereClientConfigProvider.java b/common/app/com/commercetools/sunrise/ctp/client/SphereClientConfigProvider.java index f3d6cfd53..e78128bd7 100644 --- a/common/app/com/commercetools/sunrise/ctp/client/SphereClientConfigProvider.java +++ b/common/app/com/commercetools/sunrise/ctp/client/SphereClientConfigProvider.java @@ -8,6 +8,9 @@ import javax.inject.Inject; +/** + * Provides a {@link SphereClientConfig} extracted from the application's configuration. + */ public final class SphereClientConfigProvider implements Provider { private static final String CONFIG_ROOT = "sunrise.ctp.client"; diff --git a/common/app/com/commercetools/sunrise/ctp/client/SphereClientModule.java b/common/app/com/commercetools/sunrise/ctp/client/SphereClientModule.java new file mode 100644 index 000000000..32389817c --- /dev/null +++ b/common/app/com/commercetools/sunrise/ctp/client/SphereClientModule.java @@ -0,0 +1,25 @@ +package com.commercetools.sunrise.ctp.client; + +import com.commercetools.sunrise.framework.controllers.metrics.SimpleMetricsSphereClientProvider; +import com.google.inject.AbstractModule; +import io.sphere.sdk.client.SphereClient; +import io.sphere.sdk.client.SphereClientConfig; + +import javax.inject.Singleton; + +/** + * Module that allows to inject a {@link SphereClient} and its configuration. + */ +public final class SphereClientModule extends AbstractModule { + + @Override + protected void configure() { + bind(SphereClientConfig.class) + .toProvider(SphereClientConfigProvider.class) + .in(Singleton.class); + + bind(SphereClient.class) + .toProvider(SimpleMetricsSphereClientProvider.class) + .in(Singleton.class); + } +} diff --git a/common/app/com/commercetools/sunrise/framework/localization/ProjectContext.java b/common/app/com/commercetools/sunrise/ctp/project/ProjectContext.java similarity index 78% rename from common/app/com/commercetools/sunrise/framework/localization/ProjectContext.java rename to common/app/com/commercetools/sunrise/ctp/project/ProjectContext.java index 4542b3f85..f245da07c 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/ProjectContext.java +++ b/common/app/com/commercetools/sunrise/ctp/project/ProjectContext.java @@ -1,7 +1,12 @@ -package com.commercetools.sunrise.framework.localization; +package com.commercetools.sunrise.ctp.project; +import com.commercetools.sunrise.framework.localization.NoCountryFoundException; +import com.commercetools.sunrise.framework.localization.NoCurrencyFoundException; +import com.commercetools.sunrise.framework.localization.NoLocaleFoundException; import com.google.inject.ImplementedBy; import com.neovisionaries.i18n.CountryCode; +import io.sphere.sdk.projects.Project; +import play.Configuration; import javax.money.CurrencyUnit; import java.util.List; @@ -64,4 +69,8 @@ default boolean isCountrySupported(final CountryCode countryCode) { default boolean isCurrencySupported(final CurrencyUnit currency) { return currencies().contains(currency); } + + static ProjectContext of(final Configuration globalConfig, final String configPath, final Project project) { + return new ProjectContextImpl(globalConfig, configPath, project); + } } diff --git a/common/app/com/commercetools/sunrise/framework/localization/ProjectContextImpl.java b/common/app/com/commercetools/sunrise/ctp/project/ProjectContextImpl.java similarity index 59% rename from common/app/com/commercetools/sunrise/framework/localization/ProjectContextImpl.java rename to common/app/com/commercetools/sunrise/ctp/project/ProjectContextImpl.java index dce43db31..cd4ff4f1c 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/ProjectContextImpl.java +++ b/common/app/com/commercetools/sunrise/ctp/project/ProjectContextImpl.java @@ -1,13 +1,9 @@ -package com.commercetools.sunrise.framework.localization; +package com.commercetools.sunrise.ctp.project; import com.commercetools.sunrise.play.configuration.SunriseConfigurationException; import com.neovisionaries.i18n.CountryCode; -import io.sphere.sdk.client.SphereClient; -import io.sphere.sdk.client.SphereRequest; -import io.sphere.sdk.client.SphereTimeoutException; import io.sphere.sdk.models.Base; import io.sphere.sdk.projects.Project; -import io.sphere.sdk.projects.queries.ProjectGet; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import play.Configuration; @@ -16,12 +12,10 @@ import javax.inject.Singleton; import javax.money.CurrencyUnit; import javax.money.Monetary; -import java.time.Duration; import java.util.List; import java.util.Locale; import java.util.function.Function; -import static io.sphere.sdk.client.SphereClientUtils.blockingWait; import static java.util.Collections.emptyList; import static java.util.stream.Collectors.toList; @@ -34,26 +28,22 @@ final class ProjectContextImpl extends Base implements ProjectContext { private static final Logger LOGGER = LoggerFactory.getLogger(ProjectContext.class); - private static final String CONFIG_LANGUAGES = "application.i18n.languages"; - private static final String CONFIG_COUNTRIES = "application.countries"; - private static final String CONFIG_CURRENCIES = "application.currencies"; private final List locales; private final List countryCodes; private final List currencies; @Inject - ProjectContextImpl(final Configuration configuration, final SphereClient client) { - try { - final SphereRequest request = ProjectGet.of(); - final Project project = blockingWait(client.execute(request), Duration.ofMinutes(1)); - this.locales = projectLocales(configuration, project); - this.countryCodes = projectCountries(configuration, project); - this.currencies = projectCurrencies(configuration, project); - LOGGER.debug("Project Languages {}, Countries {}, Currencies {}", locales, countryCodes, currencies); - } catch (SphereTimeoutException e) { - throw new RuntimeException("Could not fetch project information", e); - } + ProjectContextImpl(final Configuration globalConfig, final Project project) { + this(globalConfig, "sunrise.ctp.project", project); + } + + ProjectContextImpl(final Configuration globalConfig, final String configPath, final Project project) { + final Configuration config = globalConfig.getConfig(configPath); + this.locales = projectLocales(config, project); + this.countryCodes = projectCountries(config, project); + this.currencies = projectCurrencies(config, project); + LOGGER.debug("Initialized ProjectContext: Languages {}, Countries {}, Currencies {}", locales, countryCodes, currencies); } @Override @@ -72,15 +62,15 @@ public List currencies() { } private static List projectLocales(final Configuration configuration, final Project project) { - return getValues(configuration, CONFIG_LANGUAGES, Locale::forLanguageTag, project.getLanguageLocales()); + return getValues(configuration, "languages", Locale::forLanguageTag, project.getLanguageLocales()); } private static List projectCountries(final Configuration configuration, final Project project) { - return getValues(configuration, CONFIG_COUNTRIES, CountryCode::getByCode, project.getCountries()); + return getValues(configuration, "countries", CountryCode::getByCode, project.getCountries()); } private static List projectCurrencies(final Configuration configuration, final Project project) { - return getValues(configuration, CONFIG_CURRENCIES, Monetary::getCurrency, project.getCurrencyUnits()); + return getValues(configuration, "currencies", Monetary::getCurrency, project.getCurrencyUnits()); } private static List getValues(final Configuration configuration, final String configKey, @@ -94,4 +84,4 @@ private static List getValues(final Configuration configuration, final St } return values; } -} +} \ No newline at end of file diff --git a/common/app/com/commercetools/sunrise/ctp/project/ProjectModule.java b/common/app/com/commercetools/sunrise/ctp/project/ProjectModule.java new file mode 100644 index 000000000..e40c55d56 --- /dev/null +++ b/common/app/com/commercetools/sunrise/ctp/project/ProjectModule.java @@ -0,0 +1,19 @@ +package com.commercetools.sunrise.ctp.project; + +import com.google.inject.AbstractModule; +import io.sphere.sdk.projects.Project; + +import javax.inject.Singleton; + +/** + * Module that allows to inject a commercetools {@link Project}. + */ +public final class ProjectModule extends AbstractModule { + + @Override + protected void configure() { + bind(Project.class) + .toProvider(ProjectProvider.class) + .in(Singleton.class); + } +} diff --git a/common/app/com/commercetools/sunrise/ctp/project/ProjectProvider.java b/common/app/com/commercetools/sunrise/ctp/project/ProjectProvider.java new file mode 100644 index 000000000..050bbc9e0 --- /dev/null +++ b/common/app/com/commercetools/sunrise/ctp/project/ProjectProvider.java @@ -0,0 +1,31 @@ +package com.commercetools.sunrise.ctp.project; + +import io.sphere.sdk.client.SphereClient; +import io.sphere.sdk.client.SphereRequest; +import io.sphere.sdk.projects.Project; +import io.sphere.sdk.projects.queries.ProjectGet; + +import javax.inject.Inject; +import javax.inject.Provider; +import java.time.Duration; + +import static io.sphere.sdk.client.SphereClientUtils.blockingWait; + +/** + * Provides the commercetools {@link Project} associated with the injected {@link SphereClient}. + */ +public final class ProjectProvider implements Provider { + + private final SphereClient sphereClient; + + @Inject + ProjectProvider(final SphereClient sphereClient) { + this.sphereClient = sphereClient; + } + + @Override + public Project get() { + final SphereRequest request = ProjectGet.of(); + return blockingWait(sphereClient.execute(request), Duration.ofSeconds(30)); + } +} diff --git a/common/app/com/commercetools/sunrise/framework/controllers/metrics/SimpleMetricsSphereClientProvider.java b/common/app/com/commercetools/sunrise/framework/controllers/metrics/SimpleMetricsSphereClientProvider.java index 61a6d495f..694f2cf8f 100644 --- a/common/app/com/commercetools/sunrise/framework/controllers/metrics/SimpleMetricsSphereClientProvider.java +++ b/common/app/com/commercetools/sunrise/framework/controllers/metrics/SimpleMetricsSphereClientProvider.java @@ -11,13 +11,16 @@ import static java.util.concurrent.CompletableFuture.completedFuture; +/** + * Provides a {@link SphereClient} using the {@link SimpleMetricsSphereClient} implementation. + */ public final class SimpleMetricsSphereClientProvider implements Provider { private final ApplicationLifecycle applicationLifecycle; private final SphereClientConfig sphereClientConfig; @Inject - public SimpleMetricsSphereClientProvider(final ApplicationLifecycle applicationLifecycle, final SphereClientConfig sphereClientConfig) { + SimpleMetricsSphereClientProvider(final ApplicationLifecycle applicationLifecycle, final SphereClientConfig sphereClientConfig) { this.applicationLifecycle = applicationLifecycle; this.sphereClientConfig = sphereClientConfig; } diff --git a/common/app/com/commercetools/sunrise/framework/injection/SunriseModule.java b/common/app/com/commercetools/sunrise/framework/injection/SunriseModule.java index b7379fc5a..f7de4d5d6 100644 --- a/common/app/com/commercetools/sunrise/framework/injection/SunriseModule.java +++ b/common/app/com/commercetools/sunrise/framework/injection/SunriseModule.java @@ -1,21 +1,17 @@ package com.commercetools.sunrise.framework.injection; -import com.commercetools.sunrise.ctp.client.SphereClientConfigProvider; import com.google.inject.AbstractModule; -import io.sphere.sdk.client.SphereClientConfig; import io.sphere.sdk.utils.MoneyImpl; -import javax.inject.Singleton; import javax.money.Monetary; import javax.money.format.MonetaryFormats; -public class SunriseModule extends AbstractModule { +public final class SunriseModule extends AbstractModule { @Override protected void configure() { applyJavaMoneyHack(); bindScope(RequestScoped.class, new RequestScope()); - bind(SphereClientConfig.class).toProvider(SphereClientConfigProvider.class).in(Singleton.class); } private void applyJavaMoneyHack() { diff --git a/common/app/com/commercetools/sunrise/framework/localization/CountryFromSessionProvider.java b/common/app/com/commercetools/sunrise/framework/localization/CountryFromSessionProvider.java index 7e51f72cf..7b9e7cc81 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/CountryFromSessionProvider.java +++ b/common/app/com/commercetools/sunrise/framework/localization/CountryFromSessionProvider.java @@ -1,5 +1,6 @@ package com.commercetools.sunrise.framework.localization; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.sessions.country.CountryInSession; import com.neovisionaries.i18n.CountryCode; @@ -7,13 +8,17 @@ import javax.inject.Provider; import java.util.Optional; +/** + * Provides the {@link CountryCode} instance of the country saved in the user's session. + * If not set, it provides the default country from the project. + */ public final class CountryFromSessionProvider implements Provider { private final ProjectContext projectContext; private final CountryInSession countryInSession; @Inject - public CountryFromSessionProvider(final ProjectContext projectContext, final CountryInSession countryInSession) { + CountryFromSessionProvider(final ProjectContext projectContext, final CountryInSession countryInSession) { this.projectContext = projectContext; this.countryInSession = countryInSession; } diff --git a/common/app/com/commercetools/sunrise/framework/localization/CurrencyFromCountryProvider.java b/common/app/com/commercetools/sunrise/framework/localization/CurrencyFromCountryProvider.java index cde445ca6..ccb47cd49 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/CurrencyFromCountryProvider.java +++ b/common/app/com/commercetools/sunrise/framework/localization/CurrencyFromCountryProvider.java @@ -1,5 +1,6 @@ package com.commercetools.sunrise.framework.localization; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.neovisionaries.i18n.CountryCode; import javax.inject.Inject; @@ -8,13 +9,16 @@ import javax.money.Monetary; import java.util.Optional; +/** + * Provides the {@link CurrencyUnit} corresponding to the injected {@link CountryCode}. + */ public final class CurrencyFromCountryProvider implements Provider { private final CountryCode country; private final ProjectContext projectContext; @Inject - public CurrencyFromCountryProvider(final CountryCode country, final ProjectContext projectContext) { + CurrencyFromCountryProvider(final CountryCode country, final ProjectContext projectContext) { this.country = country; this.projectContext = projectContext; } diff --git a/common/app/com/commercetools/sunrise/framework/localization/LocaleFromUrlProvider.java b/common/app/com/commercetools/sunrise/framework/localization/LocaleFromUrlProvider.java index 916942262..f4817e87d 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/LocaleFromUrlProvider.java +++ b/common/app/com/commercetools/sunrise/framework/localization/LocaleFromUrlProvider.java @@ -1,5 +1,6 @@ package com.commercetools.sunrise.framework.localization; +import com.commercetools.sunrise.ctp.project.ProjectContext; import play.mvc.Http; import javax.inject.Inject; @@ -10,12 +11,17 @@ import static java.util.Arrays.asList; +/** + * Provides the {@link Locale} instance extracted from the URL using {@code languageTag} as the route variable name. + */ public final class LocaleFromUrlProvider implements Provider { + private static final String ROUTE_LANGUAGE_VAR = "languageTag"; + private final ProjectContext projectContext; @Inject - public LocaleFromUrlProvider(final ProjectContext projectContext) { + LocaleFromUrlProvider(final ProjectContext projectContext) { this.projectContext = projectContext; } @@ -44,7 +50,7 @@ private Optional indexOfLanguageTagInRoutePattern(final Http.Context ht .map(routePattern -> routePattern.toString().replaceAll("<[^>]+>", "")) // Remove regex because splitting '$languageTag<[^/]+>' with '/' would create more words .map(routePattern -> { final List paths = asList(routePattern.split("/")); - return paths.indexOf("$languageTag"); + return paths.indexOf("$" + ROUTE_LANGUAGE_VAR); }) .filter(index -> index >= 0); } diff --git a/common/app/com/commercetools/sunrise/framework/localization/LocalizationModule.java b/common/app/com/commercetools/sunrise/framework/localization/LocalizationModule.java new file mode 100644 index 000000000..f1aa8bb29 --- /dev/null +++ b/common/app/com/commercetools/sunrise/framework/localization/LocalizationModule.java @@ -0,0 +1,29 @@ +package com.commercetools.sunrise.framework.localization; + +import com.commercetools.sunrise.framework.injection.RequestScoped; +import com.google.inject.AbstractModule; +import com.neovisionaries.i18n.CountryCode; + +import javax.money.CurrencyUnit; +import java.util.Locale; + +/** + * Module that allows to inject locale, country and currency corresponding to the current user. + */ +public final class LocalizationModule extends AbstractModule { + + @Override + protected void configure() { + bind(Locale.class) + .toProvider(LocaleFromUrlProvider.class) + .in(RequestScoped.class); + + bind(CountryCode.class) + .toProvider(CountryFromSessionProvider.class) + .in(RequestScoped.class); + + bind(CurrencyUnit.class) + .toProvider(CurrencyFromCountryProvider.class) + .in(RequestScoped.class); + } +} diff --git a/common/app/com/commercetools/sunrise/framework/localization/UserLanguageImpl.java b/common/app/com/commercetools/sunrise/framework/localization/UserLanguageImpl.java index 73f900f61..d9ce45c3c 100644 --- a/common/app/com/commercetools/sunrise/framework/localization/UserLanguageImpl.java +++ b/common/app/com/commercetools/sunrise/framework/localization/UserLanguageImpl.java @@ -1,5 +1,6 @@ package com.commercetools.sunrise.framework.localization; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.injection.RequestScoped; import io.sphere.sdk.models.Base; import org.slf4j.Logger; diff --git a/common/app/com/commercetools/sunrise/framework/template/ThemeModule.java b/common/app/com/commercetools/sunrise/framework/template/ThemeModule.java new file mode 100644 index 000000000..b39361959 --- /dev/null +++ b/common/app/com/commercetools/sunrise/framework/template/ThemeModule.java @@ -0,0 +1,32 @@ +package com.commercetools.sunrise.framework.template; + +import com.commercetools.sunrise.cms.CmsService; +import com.commercetools.sunrise.framework.template.cms.FileBasedCmsServiceProvider; +import com.commercetools.sunrise.framework.template.engine.HandlebarsTemplateEngineProvider; +import com.commercetools.sunrise.framework.template.engine.TemplateEngine; +import com.commercetools.sunrise.framework.template.i18n.ConfigurableI18nResolverProvider; +import com.commercetools.sunrise.framework.template.i18n.I18nResolver; +import com.google.inject.AbstractModule; + +import javax.inject.Singleton; + +/** + * Module that allows to inject theme related classes, such as CMS, i18n Resolver and Template Engine. + */ +public final class ThemeModule extends AbstractModule { + + @Override + protected void configure() { + bind(CmsService.class) + .toProvider(FileBasedCmsServiceProvider.class) + .in(Singleton.class); + + bind(TemplateEngine.class) + .toProvider(HandlebarsTemplateEngineProvider.class) + .in(Singleton.class); + + bind(I18nResolver.class) + .toProvider(ConfigurableI18nResolverProvider.class) + .in(Singleton.class); + } +} diff --git a/common/app/com/commercetools/sunrise/framework/template/cms/FileBasedCmsServiceProvider.java b/common/app/com/commercetools/sunrise/framework/template/cms/FileBasedCmsServiceProvider.java index 6c9a00ca7..4e914ebb6 100644 --- a/common/app/com/commercetools/sunrise/framework/template/cms/FileBasedCmsServiceProvider.java +++ b/common/app/com/commercetools/sunrise/framework/template/cms/FileBasedCmsServiceProvider.java @@ -2,7 +2,7 @@ import com.commercetools.sunrise.cms.CmsService; import com.commercetools.sunrise.play.configuration.SunriseConfigurationException; -import com.commercetools.sunrise.framework.localization.ProjectContext; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.template.cms.filebased.FileBasedCmsService; import com.commercetools.sunrise.framework.template.i18n.composite.CompositeI18nResolver; import com.commercetools.sunrise.framework.template.i18n.composite.CompositeI18nResolverFactory; diff --git a/common/app/com/commercetools/sunrise/framework/template/i18n/ConfigurableI18nResolverProvider.java b/common/app/com/commercetools/sunrise/framework/template/i18n/ConfigurableI18nResolverProvider.java index 02834aae0..934f64e64 100644 --- a/common/app/com/commercetools/sunrise/framework/template/i18n/ConfigurableI18nResolverProvider.java +++ b/common/app/com/commercetools/sunrise/framework/template/i18n/ConfigurableI18nResolverProvider.java @@ -1,7 +1,7 @@ package com.commercetools.sunrise.framework.template.i18n; import com.commercetools.sunrise.play.configuration.SunriseConfigurationException; -import com.commercetools.sunrise.framework.localization.ProjectContext; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.template.i18n.composite.CompositeI18nResolverFactory; import com.google.inject.Provider; import play.Configuration; diff --git a/common/app/com/commercetools/sunrise/framework/viewmodels/forms/countries/CountryFormFieldViewModelFactory.java b/common/app/com/commercetools/sunrise/framework/viewmodels/forms/countries/CountryFormFieldViewModelFactory.java index e16c37c2a..573170c4a 100644 --- a/common/app/com/commercetools/sunrise/framework/viewmodels/forms/countries/CountryFormFieldViewModelFactory.java +++ b/common/app/com/commercetools/sunrise/framework/viewmodels/forms/countries/CountryFormFieldViewModelFactory.java @@ -1,6 +1,6 @@ package com.commercetools.sunrise.framework.viewmodels.forms.countries; -import com.commercetools.sunrise.framework.localization.ProjectContext; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.injection.RequestScoped; import com.commercetools.sunrise.framework.viewmodels.forms.FormFieldViewModelFactory; import com.commercetools.sunrise.framework.viewmodels.forms.FormFieldWithOptions; diff --git a/common/conf/reference.conf b/common/conf/reference.conf index 5318dbd3f..966f16b37 100644 --- a/common/conf/reference.conf +++ b/common/conf/reference.conf @@ -9,7 +9,7 @@ sunrise { # CLIENT # ~~~~~ - client = { + client { # Project key of your commercetools project. # projectKey = "your-project-key" @@ -35,7 +35,7 @@ sunrise { # CATEGORIES # ~~~~~ - categories = { + categories { # Key from the cache where to store the category tree. cacheKey = "category-tree" @@ -69,7 +69,7 @@ sunrise { # PRODUCTS # ~~~~~ - products = { + products { attributes { @@ -87,6 +87,24 @@ sunrise { secondarySelectable = [] } } + + # PROJECT + # ~~~~~ + + project { + + # Enter the list of countries as ISO country codes (e.g. DE). Default country first. + # If undefined or empty list, the application will use the countries defined in your commercetools project. + # countries = ["DE", "US", "GB", "AT", "CH"] + + # Enter the list of currencies as ISO currency codes (e.g. EUR). Default currency first. + # If undefined or empty list, the application will use the currencies defined in your commercetools project. + # currencies = ["EUR", "USD"] + + # Enter the list of languages as language tags (e.g. en-UK). Default language first. + # If undefined or empty list, the application will use the languages defined in your commercetools project. + # languages = ["en", "de", "es"] + } } } @@ -287,21 +305,6 @@ checkout.customerServiceNumber = "+49 899982996-0" # LOCALIZATION # ~~~~~ -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE COUNTRIES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of countries as ISO country codes (e.g. DE). Default country first. -#application.countries = ["DE", "US", "GB", "AT", "CH"] -application.countries = ${?COUNTRIES} - -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE CURRENCIES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of currencies as ISO currency codes (e.g. EUR). Default currency first. -#application.currencies = ["EUR", "USD"] -application.currencies = ${?CURRENCIES} - -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE LANGUAGES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of languages as language tags (e.g. en-UK). Default language first. -#application.i18n.languages = ["en", "de", "es"] -application.i18n.languages = ${?LANGUAGES} - application.i18n = { # List of i18n bundles to load. bundles = ["sunrise", "main", "banner", "catalog", "checkout", "my-account-login", "my-account"] @@ -405,6 +408,11 @@ play = { actionComposition.controllerAnnotationsFirst = true } - application.loader = "com.commercetools.sunrise.play.configuration.SunriseGuiceApplicationLoader" - modules.enabled += "com.commercetools.sunrise.framework.injection.SunriseModule" + modules { + enabled += "com.commercetools.sunrise.framework.injection.SunriseModule" + enabled += "com.commercetools.sunrise.ctp.client.SphereClientModule" + enabled += "com.commercetools.sunrise.ctp.project.ProjectModule" + enabled += "com.commercetools.sunrise.framework.localization.LocalizationModule" + enabled += "com.commercetools.sunrise.framework.template.ThemeModule" + } } diff --git a/common/pt/com/commercetools/sunrise/ctp/categories/CategoriesSettingsTest.java b/common/pt/com/commercetools/sunrise/ctp/categories/CategoriesSettingsTest.java index e01223ee0..0163571b4 100644 --- a/common/pt/com/commercetools/sunrise/ctp/categories/CategoriesSettingsTest.java +++ b/common/pt/com/commercetools/sunrise/ctp/categories/CategoriesSettingsTest.java @@ -1,22 +1,12 @@ package com.commercetools.sunrise.ctp.categories; import org.junit.Test; -import play.Application; -import play.Configuration; -import play.inject.guice.GuiceApplicationBuilder; import play.test.WithApplication; import static org.assertj.core.api.Assertions.assertThat; public class CategoriesSettingsTest extends WithApplication { - @Override - protected Application provideApplication() { - return new GuiceApplicationBuilder() - .configure(Configuration.empty()) - .build(); - } - @Test public void fallbacksToDefaultValues() throws Exception { final CategoriesSettings categoriesSettings = app.injector().instanceOf(CategoriesSettings.class); diff --git a/common/pt/com/commercetools/sunrise/framework/injection/RequestScopedTest.java b/common/pt/com/commercetools/sunrise/framework/injection/RequestScopedTest.java index 5093eaf73..f031a5b59 100644 --- a/common/pt/com/commercetools/sunrise/framework/injection/RequestScopedTest.java +++ b/common/pt/com/commercetools/sunrise/framework/injection/RequestScopedTest.java @@ -15,6 +15,19 @@ public class RequestScopedTest extends WithApplication { + @Override + protected Application provideApplication() { + final Module module = new AbstractModule() { + @Override + protected void configure() { + bindScope(RequestScoped.class, new RequestScope()); + } + }; + return new GuiceApplicationBuilder() + .overrides(module) + .build(); + } + @Test public void keepsAliveInTheSameRequest() throws Exception { invokeWithContext(fakeRequest(), () -> { @@ -50,20 +63,6 @@ public void createsNewInstanceWhenNoHttpContextAvailable() throws Exception { .isNotSameAs(instance2); } - @Override - protected Application provideApplication() { - final Module module = new AbstractModule() { - @Override - protected void configure() { - final RequestScope requestScope = new RequestScope(); - bindScope(RequestScoped.class, requestScope); - } - }; - return new GuiceApplicationBuilder() - .overrides(module) - .build(); - } - @RequestScoped private static class RequestScopedClass { diff --git a/common/pt/com/commercetools/sunrise/framework/localization/UserLanguageImplTest.java b/common/pt/com/commercetools/sunrise/framework/localization/UserLanguageImplTest.java index 0d8365c4c..7d9500d85 100644 --- a/common/pt/com/commercetools/sunrise/framework/localization/UserLanguageImplTest.java +++ b/common/pt/com/commercetools/sunrise/framework/localization/UserLanguageImplTest.java @@ -1,5 +1,6 @@ package com.commercetools.sunrise.framework.localization; +import com.commercetools.sunrise.ctp.project.ProjectContext; import org.junit.Test; import play.test.WithApplication; diff --git a/common/pt/com/commercetools/sunrise/httpauth/HttpAuthenticationFilterTest.java b/common/pt/com/commercetools/sunrise/httpauth/HttpAuthenticationFilterTest.java index 56566c7e3..1862b5f19 100644 --- a/common/pt/com/commercetools/sunrise/httpauth/HttpAuthenticationFilterTest.java +++ b/common/pt/com/commercetools/sunrise/httpauth/HttpAuthenticationFilterTest.java @@ -1,7 +1,5 @@ package com.commercetools.sunrise.httpauth; -import com.google.inject.AbstractModule; -import com.google.inject.Module; import org.junit.Test; import play.Application; import play.inject.guice.GuiceApplicationBuilder; @@ -15,6 +13,7 @@ import play.test.TestServer; import static org.assertj.core.api.Assertions.assertThat; +import static play.inject.Bindings.bind; import static play.mvc.Results.ok; import static play.test.Helpers.running; @@ -23,6 +22,19 @@ public class HttpAuthenticationFilterTest { private static final String AUTHENTICATE_HEADER_CONTENT = "Auth required"; private static final String URI = "/"; + private TestServer testServer(final boolean isAuthEnabled) { + final Router router = new RoutingDsl() + .GET(URI).routeTo(() -> ok()) + .build(); + final Application app = new GuiceApplicationBuilder() + .configure("play.http.filters", "com.commercetools.sunrise.httpauth.basic.BasicHttpAuthenticationFilters") + .overrides( + bind(HttpAuthentication.class).toInstance(httpAuthentication(isAuthEnabled)), + bind(play.api.routing.Router.class).toInstance(router.asScala())) + .build(); + return Helpers.testServer(app); + } + @Test public void allowsAccessWhenDisabled() throws Exception { final TestServer testServer = testServer(false); @@ -54,24 +66,6 @@ public void unauthorizedWhenEnabled() throws Exception { }); } - private TestServer testServer(final boolean isAuthEnabled) { - final Router router = new RoutingDsl() - .GET(URI).routeTo(() -> ok()) - .build(); - final Module module = new AbstractModule() { - @Override - protected void configure() { - bind(HttpAuthentication.class).toInstance(httpAuthentication(isAuthEnabled)); - bind(play.api.routing.Router.class).toInstance(router.asScala()); - } - }; - final Application app = new GuiceApplicationBuilder() - .overrides(module) - .configure("play.http.filters", "com.commercetools.sunrise.httpauth.basic.BasicHttpAuthenticationFilters") - .build(); - return Helpers.testServer(app); - } - private static HttpAuthentication httpAuthentication(final boolean enabled) { return new HttpAuthentication() { @Override diff --git a/common/pt/com/commercetools/sunrise/httpauth/basic/BasicHttpAuthenticationFilterTest.java b/common/pt/com/commercetools/sunrise/httpauth/basic/BasicHttpAuthenticationFilterTest.java index e68eeede3..f9cd0fb48 100644 --- a/common/pt/com/commercetools/sunrise/httpauth/basic/BasicHttpAuthenticationFilterTest.java +++ b/common/pt/com/commercetools/sunrise/httpauth/basic/BasicHttpAuthenticationFilterTest.java @@ -1,8 +1,6 @@ package com.commercetools.sunrise.httpauth.basic; import com.commercetools.sunrise.httpauth.HttpAuthentication; -import com.google.inject.AbstractModule; -import com.google.inject.Module; import org.junit.Test; import play.Application; import play.inject.guice.GuiceApplicationBuilder; @@ -16,15 +14,29 @@ import play.test.WithServer; import static org.assertj.core.api.Assertions.assertThat; +import static play.inject.Bindings.bind; import static play.mvc.Results.ok; public class BasicHttpAuthenticationFilterTest extends WithServer { - private static final String USERNAME = "username"; + private static final String PASSWORD = "password"; private static final String REALM = "My Realm"; private static final String URI = "/"; + @Override + protected Application provideApplication() { + final Router router = new RoutingDsl() + .GET(URI).routeTo(() -> ok()) + .build(); + return new GuiceApplicationBuilder() + .configure("play.http.filters", "com.commercetools.sunrise.httpauth.basic.BasicHttpAuthenticationFilters") + .overrides( + bind(HttpAuthentication.class).toInstance(new BasicHttpAuthentication(REALM, USERNAME + ":" + PASSWORD)), + bind(play.api.routing.Router.class).toInstance(router.asScala())) + .build(); + } + @Test public void authorizedWhenEnabledAndCredentialsProvided() throws Exception { try (WSClient wsClient = WS.newClient(testServer.port())) { @@ -58,22 +70,4 @@ public void unauthorizedWhenEnabledAndNoCredentialsProvided() throws Exception { assertThat(response.getHeader(Http.HeaderNames.WWW_AUTHENTICATE)).contains(REALM); } } - - @Override - protected Application provideApplication() { - final Router router = new RoutingDsl() - .GET(URI).routeTo(() -> ok()) - .build(); - final Module module = new AbstractModule() { - @Override - protected void configure() { - bind(HttpAuthentication.class).toInstance(new BasicHttpAuthentication(REALM, USERNAME + ":" + PASSWORD)); - bind(play.api.routing.Router.class).toInstance(router.asScala()); - } - }; - return new GuiceApplicationBuilder() - .configure("play.http.filters", "com.commercetools.sunrise.httpauth.basic.BasicHttpAuthenticationFilters") - .overrides(module) - .build(); - } } diff --git a/common/pt/com/commercetools/sunrise/sessions/SerializableObjectStoringSessionCookieStrategyTest.java b/common/pt/com/commercetools/sunrise/sessions/SerializableObjectStoringSessionCookieStrategyTest.java index 149dd52bf..24ddeba00 100644 --- a/common/pt/com/commercetools/sunrise/sessions/SerializableObjectStoringSessionCookieStrategyTest.java +++ b/common/pt/com/commercetools/sunrise/sessions/SerializableObjectStoringSessionCookieStrategyTest.java @@ -13,7 +13,6 @@ public class SerializableObjectStoringSessionCookieStrategyTest extends WithApplication { - private static final SomeObject SOME_OBJECT = new SomeObject("hello", 2); private static final SomeObject SOME_OTHER_OBJECT = new SomeObject("world", 4); private static final String JSON_SOME_OBJECT = Json.stringify(Json.toJson(SOME_OBJECT)); diff --git a/common/test/com/commercetools/sunrise/framework/localization/ProjectContextTest.java b/common/test/com/commercetools/sunrise/ctp/project/ProjectContextTest.java similarity index 80% rename from common/test/com/commercetools/sunrise/framework/localization/ProjectContextTest.java rename to common/test/com/commercetools/sunrise/ctp/project/ProjectContextTest.java index 92a03f13e..ec01fd18a 100644 --- a/common/test/com/commercetools/sunrise/framework/localization/ProjectContextTest.java +++ b/common/test/com/commercetools/sunrise/ctp/project/ProjectContextTest.java @@ -1,18 +1,27 @@ -package com.commercetools.sunrise.framework.localization; +package com.commercetools.sunrise.ctp.project; +import com.commercetools.sunrise.framework.localization.NoCountryFoundException; +import com.commercetools.sunrise.framework.localization.NoCurrencyFoundException; +import com.commercetools.sunrise.framework.localization.NoLocaleFoundException; import com.neovisionaries.i18n.CountryCode; +import io.sphere.sdk.projects.Project; import org.junit.Test; +import play.Configuration; import javax.money.CurrencyUnit; import javax.money.Monetary; +import java.util.HashMap; import java.util.List; import java.util.Locale; +import java.util.Map; import static java.util.Arrays.asList; import static java.util.Collections.emptyList; +import static java.util.Collections.singletonMap; import static java.util.Locale.*; import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatThrownBy; +import static org.mockito.Mockito.mock; public class ProjectContextTest { @@ -106,6 +115,21 @@ public void throwsExceptionOnOnlyNullCurrencies() throws Exception { .hasMessageContaining("Project does not have any valid currency unit associated"); } + @Test + public void createsInstanceWithStaticConstructor() throws Exception { + final Map map = new HashMap<>(); + map.put("languages", asList("de", "en-US")); + map.put("countries", asList("DE", "US")); + map.put("currencies", asList("EUR", "USD")); + final Configuration configuration = new Configuration(singletonMap("foo", map)); + + final Project dummyProject = mock(Project.class); + final ProjectContext projectContext = ProjectContext.of(configuration, "foo", dummyProject); + assertThat(projectContext.locales()).containsExactly(Locale.GERMAN, Locale.US); + assertThat(projectContext.countries()).containsExactly(CountryCode.DE, CountryCode.US); + assertThat(projectContext.currencies()).containsExactly(EUR, USD); + } + private static ProjectContext createProjectContext(final List locales, final List countries, final List currencies) { return new ProjectContext() { diff --git a/conf/application.conf b/conf/application.conf index 06d31716f..857f09990 100644 --- a/conf/application.conf +++ b/conf/application.conf @@ -262,21 +262,6 @@ checkout.customerServiceNumber = "+49 899982996-0" # LOCALIZATION # ~~~~~ -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE COUNTRIES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of countries as ISO country codes (e.g. DE). Default country first. -#application.countries = ["DE", "US", "GB", "AT", "CH"] -application.countries = ${?COUNTRIES} - -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE CURRENCIES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of currencies as ISO currency codes (e.g. EUR). Default currency first. -#application.currencies = ["EUR", "USD"] -application.currencies = ${?CURRENCIES} - -# LEAVE COMMENTED IF YOU WANT THE APPLICATION TO USE THE LANGUAGES DEFINED IN YOUR COMMERCETOOLS PROJECT! -# In case you want to replace them, enter the list of languages as language tags (e.g. en-UK). Default language first. -#application.i18n.languages = ["en", "de", "es"] -application.i18n.languages = ${?LANGUAGES} - application.i18n = { # List of i18n bundles to load. bundles = ["sunrise", "main", "banner", "catalog", "checkout", "my-account-login", "my-account"] @@ -360,13 +345,7 @@ play = { crypto.secret="changeme" crypto.secret=${?APPLICATION_SECRET} - http = { - errorHandler = "com.commercetools.sunrise.play.http.SunriseDefaultHttpErrorHandler" - actionComposition.controllerAnnotationsFirst = true - } - application.loader = "com.commercetools.sunrise.play.configuration.SunriseGuiceApplicationLoader" - modules.enabled += "com.commercetools.sunrise.framework.injection.SunriseModule" } include "dev" \ No newline at end of file diff --git a/shopping-cart/app/com/commercetools/sunrise/shoppingcart/checkout/payment/PaymentSettingsImpl.java b/shopping-cart/app/com/commercetools/sunrise/shoppingcart/checkout/payment/PaymentSettingsImpl.java index db50703fa..6dbb652c1 100644 --- a/shopping-cart/app/com/commercetools/sunrise/shoppingcart/checkout/payment/PaymentSettingsImpl.java +++ b/shopping-cart/app/com/commercetools/sunrise/shoppingcart/checkout/payment/PaymentSettingsImpl.java @@ -1,6 +1,6 @@ package com.commercetools.sunrise.shoppingcart.checkout.payment; -import com.commercetools.sunrise.framework.localization.ProjectContext; +import com.commercetools.sunrise.ctp.project.ProjectContext; import com.commercetools.sunrise.framework.template.i18n.I18nIdentifier; import com.commercetools.sunrise.framework.template.i18n.I18nIdentifierFactory; import com.commercetools.sunrise.framework.template.i18n.I18nResolver; diff --git a/test-lib/app/com/commercetools/sunrise/test/JsonUtils.java b/test-lib/app/com/commercetools/sunrise/test/JsonUtils.java index 9246f7cfb..8ebf47574 100644 --- a/test-lib/app/com/commercetools/sunrise/test/JsonUtils.java +++ b/test-lib/app/com/commercetools/sunrise/test/JsonUtils.java @@ -3,7 +3,7 @@ import com.fasterxml.jackson.core.type.TypeReference; import io.sphere.sdk.json.SphereJsonUtils; -public class JsonUtils { +public final class JsonUtils { public static T readCtpObject(final String resourcePath, final TypeReference typeReference) { return SphereJsonUtils.readObjectFromResource(resourcePath, typeReference);