如何使用Spring MVC正确加载Firebase ServiceAccount json资源?

时间:2017-12-16 23:45:33

标签: json spring-mvc firebase resources filenotfoundexception

我试图将我的Spring MVC(不是Spring Boot)应用程序连接到Firebase。我的应用程序的文件夹结构如下所示:

folder structure

问题在于我不知道api key json文件的放置位置,如何加载资源以及方法调用的正确顺序。

我尝试按照下面显示的方式加载资源。在此之前,我也尝试使用ClassLoader从WEB-INF文件夹加载它并且它工作,但是更改了代码并继续接收NullPointer异常(为什么不是FileNotFound异常?),用于InputStream并且无法恢复以前的状态。

对于当前状态,我一直收到FileNotFound Exception,因为我无法加载资源,无论我用Google搜索多少" Spring MVC加载资源"当我检查调试器时,服务帐户" init" @PostConstruct的方法在启动服务器时没有运行。

我知道我应该能够加载资源并调用" init"方法,以使其工作。 (我认为在创建bean之后和使用firebase方法之前调用它已经足够了)但是我无法想出一个可行的实现。

我用过这里的例子: https://github.com/savicprvoslav/Spring-Boot-starter (页面底部)

我的控制器类:

@Controller
@RequestMapping("/firebase")
public class FirebaseController {

    @Autowired
    private FirebaseService firebaseService;

    @GetMapping(value="/upload/maincategories")
    public void uploadMainRecordCategories() {

        firebaseService.uploadMainRecordCategories();
    }

我的服务类:

@Service
public class FirebaseServiceBean implements FirebaseService {

    @Value("/api.json")
    Resource apiKey;

@Override
public void uploadMainRecordCategories() {
  // do something
}

    @PostConstruct
    public void init() {

        try (InputStream serviceAccount = apiKey.getInputStream()) { 

            FirebaseOptions options = new FirebaseOptions.Builder()
                    .setCredentials(GoogleCredentials.fromStream(serviceAccount))
                    .setDatabaseUrl(FirebaseStringValue.DB_URL).build();

            FirebaseApp.initializeApp(options);

        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

1 个答案:

答案 0 :(得分:0)

如何在spring属性中保存值并使用@Value(" $ {firebase.apiKey}")?

或者,将属性路径保存到文件中并引用@Value()

中的文件
@Value("${service.account.path}")
private String serviceAccountPath;

在application.properties中:

service.account.path = /path/to/service-account.json

然后配置代码:

private String getAccessToken() throws IOException {
    GoogleCredential googleCredential = GoogleCredential
            .fromStream(getServiceAccountInputStream())
            .createScoped(Collections.singletonList("https://www.googleapis.com/auth/firebase.messaging"));
    googleCredential.refreshToken();
    return googleCredential.getAccessToken();
}

private InputStream getServiceAccountInputStream() {
    File file = new File(serviceAccountPath);
    try {
        return new FileInputStream(file);
    } catch (FileNotFoundException e) {
        throw new RuntimeException("Couldn't find service-account.json");
    }
}