Como você obtém o perfil de ambiente ativo / padrão atual programaticamente no Spring?

155

Preciso codificar lógica diferente com base no perfil de ambiente atual diferente. Como você pode obter os perfis ativos e padrão atuais do Spring?

Bobo
fonte
3
@aweigold: obtenha o perfil de ambiente ativo / padrão atual programaticamente na primavera 3.1. que mais detalhes você precisa?
Bobo

Respostas:

75

Estendendo a boa e simples resposta de User1648825 (não posso comentar e minha edição foi rejeitada):

@Value("${spring.profiles.active}")
private String activeProfile;

Isso pode gerar uma IllegalArgumentException se nenhum perfil estiver definido (eu recebo um valor nulo). Isso pode ser uma coisa boa se você precisar que seja definido; caso contrário, use a sintaxe 'padrão' para @Value, ou seja:

@Value("${spring.profiles.active:Unknown}")
private String activeProfile;

... activeProfile agora contém 'Desconhecido' se spring.profiles.active não pôde ser resolvido

MartinMlima
fonte
Os nomes dos perfis são separados por vírgula. Caixa baeldung.com/spring-profiles#2-using-springactiveprofile
Jason
56

Aqui está um exemplo mais completo.

Ambiente Autowire

Primeiro, você desejará conectar automaticamente o bean de ambiente.

@Autowired
private Environment environment;

Verifique se existem perfis no Active Profiles

Em seguida, você pode usar getActiveProfiles()para descobrir se o perfil existe na lista de perfis ativos. Aqui está um exemplo que pega String[]from getActiveProfiles(), obtém um fluxo dessa matriz e usa matchers para verificar vários perfis (sem distinção entre maiúsculas e minúsculas) que retornam um valor booleano, se existirem.

//Check if Active profiles contains "local" or "test"
if(Arrays.stream(environment.getActiveProfiles()).anyMatch(
   env -> (env.equalsIgnoreCase("test") 
   || env.equalsIgnoreCase("local")) )) 
{
   doSomethingForLocalOrTest();
}
//Check if Active profiles contains "prod"
else if(Arrays.stream(environment.getActiveProfiles()).anyMatch(
   env -> (env.equalsIgnoreCase("prod")) )) 
{
   doSomethingForProd();
}

Você também pode obter funcionalidade semelhante usando os @Profile("local")Perfis de anotação que permitem a configuração seletiva com base em um parâmetro passado ou no ambiente. Aqui estão mais informações sobre esta técnica: Perfis de mola

anataliocs
fonte
2
@ Profile parece ser a melhor solução.
Paul Waldo
Estou cego por linhas separadas para cada aparelho. Não padrões de codificação Java.
user1567291 17/01
26
@Value("${spring.profiles.active}")
private String activeProfile;

Funciona e você não precisa implementar o EnvironmentAware. Mas não conheço desvantagens dessa abordagem.

user1648825
fonte
3
Esta linha dá esse erro:Caused by: java.lang.IllegalArgumentException: Could not resolve placeholder 'spring.profiles.active' in value "${spring.profiles.active}"
zygimantus
Funciona perfeitamente para mim. Usando o Spring Boot 1.5.15.
рüффп
Eu acho que se o perfil estiver definido, o valor será analisado, caso contrário, a exceção surgirá. Não serve para todas as situações.
WesternGun 14/01/19
1
O perfil ativo também pode ser uma matriz, preste atenção a isso, por favor. Dessa forma, você pode obter um erro inesperado ao adicionar perfis adicionais.
Alex Efimov
A desvantagem dessa abordagem é que ela não obtém todos os perfis que o Spring pode considerar ao avaliar @Profile. Os aplicativos também podem usar a spring.profiles.include propriedade e podem definir perfis programaticamente durante a inicialização usando ConfigurableEnvironment. Environment.getActiveProfiles()obterá a lista completa dos perfis definidos usando qualquer um desses mecanismos.
Scott Frederick
14

Se você não estiver usando fiação automática, basta implementar EnvironmentAware

Arnout Engelen
fonte
0

Parece que há alguma demanda para poder acessar isso estaticamente.

Como posso obter essa coisa em métodos estáticos em classes não gerenciadas por mola? - Aetherus

É um truque, mas você pode escrever sua própria classe para expô-lo. Você deve ter cuidado para garantir que nada será chamado SpringContext.getEnvironment()antes que todos os beans tenham sido criados, pois não há garantia de quando esse componente será instanciado.

@Component
public class SpringContext
{
    private static Environment environment;

    public SpringContext(Environment environment) {
        SpringContext.environment = environment;
    }

    public static Environment getEnvironment() {
        if (environment == null) {
            throw new RuntimeException("Environment has not been set yet");
        }
        return environment;
    }
}
Michael
fonte