class Google::Workspace::ApplicationService < ApplicationService
  def initialize(config)
    @config = config
  end

  def access_token
    response = request(:post, 'https://oauth2.googleapis.com/token', {}, body: token_parameters)
    response[:access_token]
  rescue
    false
  end

  private
    def token_parameters
      {
        grant_type: 'urn:ietf:params:oauth:grant-type:jwt-bearer',
        assertion: encoded_token
      }
    end

    def encoded_token
      JWT.encode(payload, rsa_key, 'RS256', alg: 'RS256', typ: 'JWT')
    end

    def payload
      {
        iss: 'sycamore-development@sycamore-school-dev.iam.gserviceaccount.com',
        sub: @config.email,
        scope: scopes.join(' '),
        aud: 'https://oauth2.googleapis.com/token',
        exp: (time + 60.minutes).to_i,
        iat: time.to_i
      }
    end

    def rsa_key
      OpenSSL::PKey::RSA.new(File.read('config/secrets/google_service_rs256.key'))
    end

    def time
      @time ||= Time.zone.now
    end

    def authorization_header
      { Authorization: "Bearer #{access_token}", 'Content-Type': 'application/json' }
    end

    def request(method, path, headers=nil, body: {})
      headers ||= authorization_header
      json_parse(
        RestClient::Request.execute(method: method, url: path, headers: headers, payload: body)
      )
    end
end
